[C++] getline , tablice , VC++


(Kalin 93) #1

Wiec tak , wczytuje sobie 5 znaków poprzez getline , zapisuje je w tablicy ale gdy chce wyświetlić tablice to pokazuje mi to co odczytało ale przy okazji mnóstwo krzaczków , wie ktoś może czym jest to spowodowane ? :slight_smile:

char aTemp [20];

	ifstream fSave("save.dat");

	if (!fSave.good()) return 0;

	fSave.read (aTemp , 5);

	cout << aTemp;

Tak to wygląda kodowo :slight_smile:


(Fiołek) #2

Nie ma NULL-a w tablicy. Każdy ciąg znaków jest tzw. c-stringiem(chyba, że tworzysz je ręcznie) czyli ciągiem znaków zakończonym NULL-em(0). Strumienie C++ wypisują znaki dopóki nie napotkają tego znaku, jeśli go nie ustawiłeś to wypiszą Ci wszystko co jest za wartościami ustawionymi przez Ciebie.


(Kalin 93) #3

Sęk w tym że wyświetla mi ten znak (0) na końcu tablicy , kiedy używałem Dev'a nie miałem takich problemów .

Takie coś mi drukuje

agsdg╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠(ŤÁ#\ ↕0 █◄►▼▲ █◄►▼▲ █◄►▼▲ █◄►▼▲ █◄►▼▲ █◄►▼▲ █◄►▼▲ █◄►▼▲

"agsdg╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠╠(ŤÁ#\ :arrow_up_down:0" to jest tablica , niewyzerowana tylko wrzuconych 5 znaków w nią , rozumiem to , ale skąd sie biorą pozostałe znaki ?


(Sawyer47) #4

Przecież Fiołek ci napisał, cout czyta aż do napotkaniu wartości NULL, czyli przechodzi wczytane dane, tablicę i jeszcze obszary pamięci poza nią aż napotka przypadkowo NULL. Znak 0 to nie jest wartość NULL (patrz: ASCII). NULL ma kod zero, a znak '0' ma kod 48.


(Kalin 93) #5

Ok już rozumiem thx :wink:


(Sawyer47) #6

Dodam, że przy każdym uruchomieniu dostaniesz inne dane (wartości niezainicjowanych zmiennych są niezdefiniowane). To tylko przypadek, że gdzieś tam dalej w pamięci jest NULL. Możesz albo posłużyć się pętlą aby wyświetlić ustaloną liczbę elementów z tablicy, albo klasą std::string do wygodnego operowania na łańcuchach znaków.


(Kalin 93) #7

Z tym problemem się już uporałem , to była wina innej funkcji :slight_smile:

Teraz kolejny problem a mianowicie

#include 

#include 

#include 


using namespace std;


int main ()

{

	ifstream iPlik ("save.dat");

	char cTemp [5] [100];

	for (int i = 0; i<=4 ; i++) iPlik.getline (cTemp[i], 9);

	cout << cTemp;

	_getch ();

}

Ten kod powinien mi odczytać plik i wyświetlić tablice , jednak coś nie bardzo chce i drukuje mi na ekranie

0012FCCC

i na tym koniec.


(Rafal M F) #8

Spróbuj:

for(int i=0;i<5;i++)cout << cTemp[i] << endl;

Edit: Nie lepiej używać string, zamiast napisów w stylu C? A zamiast _getch() z conio.h można użyć:

system("pause");

z iostream.


(Sawyer47) #9

Bo w ten sposób nie wyświetlisz tablicy. Ponieważ wysyłasz do strumienia wskaźnik to wyświetlany jest jego adres (wyjątkiem są wskaźniki do char, wtedy wyświetlane są znaki aż do znaku NULL). Może użyjesz std::string zamiast tablic?

Edit:;

Co to za głupoty? Od kiedy system() jest z iostream? Poza tym system("pause") jest nieprzenośne :stuck_out_tongue:


(Kalin 93) #10
#include 

#include 

#include 

#include 


using namespace std;


int main ()

{

	ifstream iPlik ("save.dat");

	string sTemp [5];

	for (int i = 0; i<=4 ; i++)

	{

		iPlik.getline (sTemp[i], 9); 

		cout << sTemp [i] << endl;

	};

	_getch ();

}

Jest string i błąd też :wink:

c:\documents and settings\kalin\pulpit\a\a\a.cpp(14) : error C2664: 'std::basic_istream<_Elem,_Traits> &std::basic_istream<_Elem,_Traits>::getline(_Elem *,std::streamsize)' : cannot convert parameter 1 from 'std::string' to 'char *'

        with

        [

            _Elem=char,

            _Traits=std::char_traits

        ]

        No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called

(Rafal M F) #11

@nr47 Racja, nie ma. Coś mi się pochrzaniło. A co do przenośności to i tak klepie w VC++.

@Up: no tak. Jak już korzystasz ze string, to getline też musi być ze string, czyli będzie:

getline(iplik,sTemp[i]);

Tylko, że funkcja z string, nie przyjmuje ilości znaków do odczytania, ewentualnie jako 3-ci parametr można podać znak po napotkaniu którego ma kończyć odczytywanie, domyślnie jest to '\n'. Więcej na: http://www.cppreference.com/wiki/string/getline .


(Sawyer47) #12

No bo nie ma takiej funkcji std::getline( std::string, streamsize). Możesz użyć std::getline z std::string: http://www.cppreference.com/wiki/string/getline

Tyle, że wtedy wczytuje całą linię aż do (standardowo) '\n'.


(Kalin 93) #13

Teraz jest OK :wink: Wielkie dzięki :slight_smile:

To, że wczytuje do końca lini nie przeszkadza mi w żaden sposób :slight_smile: