[C++] wskaźnik char*

mariaaan
2012-06-22 13:51
mariaaan
0

Witam!
Dopiero zaczynam się uczyć C++ i dotarłem do wskaźników. I mam mały problem odnośnie nich,. Mianowicie chodzi mi o wskaźnik do zmiennej typu char. Gdy próbuję zrobić coś takiego:

char *wskaznik;
cout << wskaznik;

To program się wykrzacza. Natomiast gdy zamiast char jest wskaźnik do np. zmiennej typu int, float itp., to program działa i wyświetla adres jakiejś tam komórki.

Ponadto czy mógłby mi ktoś wytłumaczyć dlaczego możliwa jest instrukcja

char *wskaznik="Jakis tam tekst";

Skoro jest to wskaźnik to dlaczego taka instrukcja przypisująca mu tekst jest możliwa i program w przypadku instrukcji

cout << wskaznik;

wyświetla ów tekst przypisany wskaźnikowi.

Wiem, że moje pytania są zapewne lamerskie, ale proszę o wyrozumiałość gdyż dopiero zaczynam naukę programowania i z góry dziękuję za wszelką pomoc.

Pozostało 580 znaków

2012-06-22 14:00

Rejestracja: 9 lat temu

Ostatnio: 5 lat temu

0

Jeżeli twój kompilator pozwala na instrukcję:

char *wskaznik="Jakis tam tekst";

to odbiega od standardu. Natomiast instrukcja :

const char *wskaznik="Jakis tam tekst";

jest poprawna, gdyż kompilator traktuje "Jakis tam tekst" jako stały literał, który musi zapamiętać i umieścić gdzieś w pamięci. Instrukcja ta zwraca adres miejsca w którym umieszczony jest ten literał i przypisuje do wskaźnika. Co do drugiego pytania: operator<< dla char* jest właśnie tak zaimplementowany, że nie wyświetla adresu a literał na jaki adres wskazuje.

pozwalają chyba wszystkie, a niektóre dają warninga. - Azarien 2012-06-22 17:26
W standardzie takie przypisanie jest dozwolone (wsteczna kompatybilność z C) a kompilatory zazwyczaj warningami rzucają. - adf88 2012-06-23 11:58
Tak jest dozwolone właśnie ze względu na kompatybilność z C ale nowy standard traktuje "Jakis tam tekst" jako const char[n] - mto9 2012-06-23 12:39
w C taki zapis jest tak samo zły jak w C++ - Azarien 2012-06-23 14:33

Pozostało 580 znaków

maaariaan
2012-06-22 14:02
maaariaan
0

Używam Dev'a 4.9.9.2 :) W innym kompilatorze nie próbowałem.

Dev-C++ to nie jest kompilator... - Patryk27 2012-06-22 14:04

Pozostało 580 znaków

2012-06-22 15:09
Moderator

Rejestracja: 16 lat temu

Ostatnio: 2 godziny temu

0

Standardowo wypisywanie char* powoduje wypisywanie stringa na którego pierwszą literkę wskazuje ten wskaźnik (aż do napotkania znaku \0). Twój wskaźnik na nic nie wskazuje, więc program będzie próbował wypisywać jakieś losowe dane z losowego fragmentu pamięci i w efekcie poleci segfault.
Instrukcja:

char *wskaznik="Jakis tam tekst";

przypisuje do wskaźnika adres pierwszej literki stringa, nic więcej.


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...

Pozostało 580 znaków

maariaan
2012-06-22 15:59
maariaan
0

No dobrze więc dlaczego instrukcja

cout << wskaznik; 

wypisuje mi "jakis tam tekst" w przypadku gdy jest to wskaźnik char*, a nie adres pierwszej komórki, w której zapisana jest pierwsza litera napisu czyli "j". Natomiast gdy wskaźnik jest typu innego (int, float etc.), to na ekranie wyświetlone zostaje coś takiego "0x14", a po przypisaniu wskaźnikowi jakiejś zmiennej

int* wskaznik;
int x;
wskaznik=&x;

cout << wskaznik;

na ekranie pojawia się adres 0x22ff74.

Przepraszam, że tak męczę ale chciałbym to zrozumieć raz a porządnie. :)

Pozostało 580 znaków

2012-06-22 16:04

Rejestracja: 14 lat temu

Ostatnio: 2 dni temu

0

Wskaźnik zaimplementowany jest jako liczba oznaczająca numer komórki.
Jeżeli dasz deklarację:
int x;
i natychmiast wyświetlisz tego x:
cout<<x;
to dostaniesz jakieś śmieci.
tak samo jest ze wskaźnikiem, deklaracja:
char w;
to "w" ma w sobie jakieś śmieci, które nawet możesz obejrzeć:
cout<<(void
)w;
Natomiast jak każesz komputerowi wydrukować napis który jest pod tym adresem:
cout<<w;
to on grzecznie próbuje to wykonać.


Wykonuję programy na zamówienie, pisać na Priv.
Asm/C/C++/Pascal/Delphi/Java/C#/PHP/JS oraz inne języki.
edytowany 3x, ostatnio: _13th_Dragon, 2012-06-22 16:05

Pozostało 580 znaków

mariaan
2012-06-22 16:24
mariaan
0

Mi się wydawało, że instrukcja

char *w;
cout << x;

sprawia, że wyświetlony zostanie adres komórki na którą w wskazuje (nawet jeśli ów wskaźnik wskazuje gdzieś w maliny), a nie wypisanie napisu który się od tej komórki zaczyna. Tym bardziej, że bez przypisania wskaźnikowi "w" jakiegoś tekstu program się wykrzacza, a przy innych typach nie. Chyba, że to co widzę na ekranie w przypadku innych typów czyli wspomniane 0x14 czy też 0x22ff74 to wartość liczby, która zaczyna się tam gdzie wskazuje w (choć dziwne czemu jest to w systemie 16kowym), a nie adres jakiejś komórki w pamięci. Chyba, że chodzi o to, że kompilator traktuje inaczej wskaźnik char* (czyli jako napis i próba jego wyświetlenia jest próbą wyświetlenia napisy zaczynającego się od komórki wskazywanej przez ten wskaźnik) od wskaźników innych typów. Teraz już się totalnie pogubiłem ;/

Popnadto (taka mała dygresja):

program

int x;
cout << x;

pokazuje mi ciągle 2 (dla typu int). Z ciekawości też sprawdziłem, że coś takiego

char w="tekst";
cout <<
w;

Zgodnie z oczekiwaniami powoduje wyświetlenie na ekranie samej litery t, czyli tak jak być powinno.

Pozostało 580 znaków

2012-06-22 16:40
Moderator

Rejestracja: 16 lat temu

Ostatnio: 2 godziny temu

0

@mariaan masz rację, wydawało ci się.
Operator wypisywania jest INACZEJ zaimplementowany dla różnych typów danych. Dla każdego wskaźnika oprócz char wypisze ci adres na który wskaźnik wskazuje. Dla char wypisze ci C-stringa, czyli ciąg znaków począwszy od miejsca na które wskazuje wskaźnik aż do znaku \0


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...

Pozostało 580 znaków

mariaaan
2012-06-22 16:42
mariaaan
0

No i teraz wszystko już jest jasne (tak mi się właśnie wydaje) :) Dzięki, o to mi właśnie chodziło. :)

Pozostało 580 znaków

1 użytkowników online, w tym zalogowanych: 0, gości: 1, botów: 0