Bu kodu merak ediyorum:
cout << 'test'; // Note the single quotes.
bana bir çıktı verir 1952805748
.
Benim sorum: Çıktı bellekte bir adres mi falan?
Bu kodu merak ediyorum:
cout << 'test'; // Note the single quotes.
bana bir çıktı verir 1952805748
.
Benim sorum: Çıktı bellekte bir adres mi falan?
Yanıtlar:
Çok karakterli bir değişmez. 1952805748
olarak 0x74657374
ayrışan
0x74 -> 't'
0x65 -> 'e'
0x73 -> 's'
0x74 -> 't'
Düzenle:
C ++ standardı, §2.14.3 / 1 - Karakter değişmez değerleri
(...) Birden fazla c-char içeren sıradan bir karakter değişmezi, çok karakterli bir değişmez değerdir. Çok karakterli bir değişmezin int türü ve uygulama tanımlı değeri vardır.
sizeof(int)
uygulamanın da tanımlanmış olmasıdır. Depolama emri uygulaması sadece tanımlanmakla kalmaz, aynı zamanda bunların maksimum uzunluğu da tanımlanır.
Hayır, bu bir adres değil. Çokbaytlı karakter.
Tipik olarak, birleştirilen dört karakterin ASCII değerleri.
't' == 0x74; 'e' == 0x65; 's' == 0x73; 't' == 0x74;
Yani 0x74657374 1952805748'dir.
Ancak başka bir derleyicide 0x74736574 de olabilir. C ve C ++ standartlarının her ikisi de çok baytlı karakterlerin değerinin uygulama tanımlı olduğunu söylüyor . Bu nedenle, genel olarak kullanımı kesinlikle önerilmez.
int
çoğu makinede 4 bayt olduğu için, 4 bayttan fazla kullanmanın mantıklı olduğunu düşünmüyorum. Evet, bazı sabitleri yazmak için uygun bir yol olması amaçlanmıştı, ancak maalesef farklı derleyiciler bunu farklı şekilde yorumluyorlar, bu nedenle günümüzde çoğu kodlama stili kullanımını engelliyor.
==
Birden fazla c-char içeren sıradan bir karakter değişmezi, çok karakterli bir değişmez değerdir. Çok karakterli bir değişmezin int türü ve uygulama tanımlı değeri vardır.
Uygulama tanımlı davranışın uygulama tarafından belgelenmesi gerekir. örneğin gcc'de burada bulabilirsiniz
Derleyici bir seferde çok karakterli bir karakteri sabitler, bir önceki değeri hedef karakter başına bit sayısı kadar kaydırır ve sonra bir hedefin genişliğine kesilmiş yeni karakterin bit deseninde kayar. karakter. Son bit desenine int türü verilir ve bu nedenle, tek karakterlerin imzalanıp imzalanmadığına bakılmaksızın imzalanır.
Daha fazla ayrıntı için bu sayfadaki açıklamaya bakın
Onlar gerçekten sadece int
s. Core Audio API numaralandırmalarında, örneğin CoreAudioTypes.h
başlık dosyasında,
enum
{
kAudioFormatLinearPCM = 'lpcm',
kAudioFormatAC3 = 'ac-3',
kAudioFormat60958AC3 = 'cac3',
kAudioFormatAppleIMA4 = 'ima4',
kAudioFormatMPEG4AAC = 'aac ',
kAudioFormatMPEG4CELP = 'celp',
} ;
Bunun "platformdan bağımsız" olmadığı konusunda çok fazla sohbet var, ancak belirli bir platform için yapılmış , taşınabilirliği önemseyen bir API kullandığınızda . Aynı platformda eşitlik kontrolü asla başarısız olmaz. Bu enum
değerlerin okunması daha kolaydır ve kimliklerini aslında değerlerinde içerirler , ki bu oldukça hoştur.
Aşağıda yapmaya çalıştığım, yazdırılabilmesi için çok baytlı bir karakter değişmezidir (Mac'te bu işe yarar). Garip olan şey, 4 karakterin hepsini kullanmazsanız, sonuç aşağıda yanlış olur.
#include <stdio.h>
#define MASK(x,BYTEX) ((x&(0xff<<8*BYTEX))>>(8*BYTEX))
struct Multibyte
{
union{
int val ;
char vals[4];
};
Multibyte() : val(0) { }
Multibyte( int in )
{
vals[0] = MASK(in,3);
vals[1] = MASK(in,2);
vals[2] = MASK(in,1);
vals[3] = MASK(in,0);
}
char operator[]( int i ) {
return val >> (3-i)*8 ; // works on mac
//return val>>i*8 ; // might work on other systems
}
void println()
{
for( int i = 0 ; i < 4 ; i++ )
putc( vals[i], stdout ) ;
puts( "" ) ;
}
} ;
int main(int argc, const char * argv[])
{
Multibyte( 'abcd' ).println() ;
Multibyte( 'x097' ).println() ;
Multibyte( '\"\\\'\'' ).println() ;
Multibyte( '/*|' ).println() ;
Multibyte( 'd' ).println() ;
return 0;
}
Bu tür bir özellik, ayrıştırıcılar oluştururken gerçekten iyidir. Bunu düşün:
byte* buffer = ...;
if(*(int*)buffer == 'GET ')
invoke_get_method(buffer+4);
Bu kod muhtemelen yalnızca belirli bir endianess üzerinde çalışacak ve farklı derleyicileri kırabilir