Pojedyncze cudzysłowy vs. podwójne cudzysłowy w C lub C ++


Odpowiedzi:


282

W C i C ++ pojedyncze cudzysłowy identyfikują pojedynczy znak, podczas gdy podwójne cudzysłowy tworzą literał łańcuchowy. 'a'jest literałem pojedynczego znaku, podczas gdy "a"literałem łańcuchowym zawiera 'a'terminator i zerowy terminator (czyli tablica 2 znaków ).

W C ++ typem literału znaków jest char, ale zauważ, że w C typem literału znaków jest int, to sizeof 'a'znaczy 4 w architekturze, w której ints są 32-bitowe (a CHAR_BIT to 8), podczas gdy sizeof(char)wszędzie jest 1.


47

Niektóre kompilatory implementują także rozszerzenie, które pozwala na stosowanie stałych wieloznakowych. Standard C99 mówi:

6.4.4.4p10: „Wartość stałej liczby całkowitej zawierającej więcej niż jeden znak (np.„ Ab ”) lub zawierającej znak lub sekwencję zmiany znaczenia, która nie jest odwzorowywana na jednobajtowy znak wykonania, jest zdefiniowana w implementacji. „

Może to wyglądać na przykład tak:

const uint32_t png_ihdr = 'IHDR';

Wynikowa stała (w GCC, która to implementuje) ma wartość, którą otrzymujesz, biorąc każdy znak i przesuwając go w górę, tak że „I” kończy się na najbardziej znaczących bitach 32-bitowej wartości. Oczywiście nie powinieneś na tym polegać, jeśli piszesz niezależny od platformy kod.


7
Dzięki, właśnie widziałem to w jakimś kodzie, a moją odpowiedź można opisać tylko jako „WTF”. Używam GCC z przerwami od 15 lat i do tej pory nigdy się na to nie natknąłem.
eeeeaaii

+1 oprócz magicznych nagłówków, często używanych do oceny linii poleceń.
Wolf

28

Pojedyncze cudzysłowy to znaki ( char), podwójne cudzysłowy to ciągi zakończone znakiem null ( char *).

char c = 'x';
char *s = "Hello World";

8
„witaj świecie” to const char *.
OldSchool

@Eiko, kiedy stawiasz * infront zmiennej np. * S jak wyżej?
CodeGuru,

@CodeGuru Używasz *, gdy zmienna jest typem wskaźnika. W tym przypadku „s” wskazuje na tablicę znaków.
Eiko

16
  • 'x' jest liczbą całkowitą, reprezentującą wartość liczbową litery x w zestawie znaków maszyny
  • "x"to tablica znaków o długości dwóch znaków, po której ‘x’następuje‘\0’

2
Całkiem późno;) co jest naprawdę nowego w twojej odpowiedzi - w porównaniu z tymi już podanymi?
Wolf

10

Pojedyncze cudzysłowy dotyczą jednego znaku. Podwójne cudzysłowy odnoszą się do ciągu znaków (tablica znaków). Jeśli chcesz, możesz użyć pojedynczych cudzysłowów, aby utworzyć ciąg po jednym znaku na raz.

char myChar     = 'A';
char myString[] = "Hello Mum";
char myOtherString[] = { 'H','e','l','l','o','\0' };

10

Grzebałem w takich rzeczach jak: int cc = 'cc'; Zdarza się, że jest to w zasadzie bajtowa kopia na liczbę całkowitą. Stąd sposób, aby na to spojrzeć, polega na tym, że „cc”, czyli w zasadzie 2 c, są kopiowane do niższych 2 bajtów liczby całkowitej cc. Jeśli szukasz ciekawostek, to

printf("%d %d", 'c', 'cc'); would give:

99 25443

to dlatego, że 25443 = 99 + 256 * 99

Zatem „cc” jest stałą wieloznakową, a nie ciągiem znaków.

Twoje zdrowie



6

Podwójne cudzysłowy dotyczą literałów łańcuchowych, np .:

char str[] = "Hello world";

Pojedyncze cudzysłowy dotyczą literałów jednoznakowych, np .:

char c = 'x';

EDYCJA Jak David stwierdził w innej odpowiedzi, typ literału znaku to int.


dzięki . oznacza, że ​​znak ma 1 bajt bez znaku zerowego „/ 0” na końcu .. łańcuch zawiera znak null na końcu.
Vishwanath Dalvi,

2
@mr_eclair: Literał łańcuchowy zawsze zawiera niejawny terminator zerowy, ale bądź ostrożny. Można napisać coś podobnego char str[] = {'H','e','l','l','o'};, i strby nie mieć null terminator.
Oliver Charlesworth,

w tej sytuacji strnie jest łańcuchem (a przynajmniej łańcuchem w stylu C, który jest zdefiniowany jako NTBS).
Steve Jessop,

@ Steve: Zrozumiano. Miałem na myśli @mr_eclair, że nie wszystko, co jest char[](co ludzie często określają jako „ciągi”), jest zakończone zerem .
Oliver Charlesworth,

1
@OliCharlesworth to - na szczęście - nie pełna prawda: są dwa literały ciągów znaków oddzielone komentarza: "hello" /*seamlessly connected to*/ "world". Może to mieć sens w przypadku komentowanych wiadomości wieloliniowych.
Wolf

6

W C pojedyncze cudzysłowy, takie jak „a”, oznaczają stałe znaków, podczas gdy „a” to tablica znaków, zawsze zakończona znakiem 0


4

Pojedynczy cudzysłów służy do znakowania, a podwójny do ciągów.

Na przykład..

 printf("%c \n",'a');
 printf("%s","Hello World");

Wynik

Hello World

Jeśli użyłeś ich odwrotnie i użyłeś pojedynczego cudzysłowu dla ciągu i podwójnego cudzysłowu dla znaku. Tutaj będzie to wynik;

  printf("%c \n","a");
  printf("%s",'Hello World');

wynik :

dla pierwszego wiersza. Będziesz miał wartość śmieciową lub nieoczekiwaną. lub możesz mieć takie dane wyjściowe ..

podczas drugiego zdania. Nic nie zobaczysz. Jeszcze jedno. Jeśli masz więcej stwierdzeń po tym. Nie dadzą też żadnego rezultatu.

Uwaga: język PHP daje elastyczność w korzystaniu z pojedynczego i podwójnego cudzysłowu.


3

Pojedyncze cudzysłowy oznaczają znak, podwójne oznaczają ciąg.

W Javie jest tak samo.


2
To tak naprawdę nie wnosi żadnej wartości do pytania, ponieważ informacje te zostały już zawarte w innych odpowiedziach.
Mike Precup,

2

Użyj pojedynczego cudzysłowu z pojedynczym znakiem jako:

char ch = 'a';

tutaj 'a'jest stała char i jest równa ASCIIwartości char a.

Użyj podwójnego cudzysłowu z ciągami jako:

char str[] = "foo";

oto "foo"dosłowny ciąg znaków.

Można używać, "a"ale nie można używać „foo'

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.