Saya ingin tahu tentang kode ini:
cout << 'test'; // Note the single quotes.
memberi saya output 1952805748
.
Pertanyaan saya: Apakah output alamat dalam memori atau sesuatu?
Saya ingin tahu tentang kode ini:
cout << 'test'; // Note the single quotes.
memberi saya output 1952805748
.
Pertanyaan saya: Apakah output alamat dalam memori atau sesuatu?
Jawaban:
Ini adalah multi-karakter literal. 1952805748
adalah 0x74657374
, yang terurai menjadi
0x74 -> 't'
0x65 -> 'e'
0x73 -> 's'
0x74 -> 't'
Edit:
Standar C ++, §2.14.3 / 1 - Literal karakter
(...) Huruf karakter biasa yang berisi lebih dari satu c-char adalah multicharacter literal. Multicharacter literal memiliki tipe int dan nilai yang didefinisikan implementasi.
sizeof(int)
adalah implementasi didefinisikan juga. Jadi tidak hanya implementasi urutan penyimpanan yang ditentukan, tetapi panjang maksimumnya juga.
Tidak, ini bukan alamat. Itu yang disebut karakter multibyte.
Biasanya, ini adalah nilai ASCII dari keempat karakter yang digabungkan.
't' == 0x74; 'e' == 0x65; 's' == 0x73; 't' == 0x74;
Jadi 0x74657374 adalah 1952805748.
Tetapi bisa juga 0x74736574 pada beberapa kompiler lain. Standar C dan C ++ keduanya mengatakan nilai karakter multibyte adalah implementasi yang didefinisikan . Jadi umumnya penggunaannya sangat tidak dianjurkan.
int
4 byte pada kebanyakan mesin, saya pikir tidak masuk akal untuk menggunakan lebih dari 4 byte. Ya, itu dimaksudkan sebagai cara yang nyaman untuk menulis beberapa konstanta, tetapi sayangnya kompiler yang berbeda telah menafsirkannya secara berbeda, jadi saat ini sebagian besar gaya pengkodean mencegah penggunaannya.
==
harus diperiksa
Literal karakter biasa yang berisi lebih dari satu c-char adalah multicharacter literal. Multicharacter literal memiliki tipe int dan nilai yang didefinisikan implementasi.
Perilaku yang ditentukan implementasi harus didokumentasikan oleh implementasi. misalnya di gcc Anda dapat menemukannya di sini
Compiler menilai karakter multi-karakter yang konstan pada satu karakter pada suatu waktu, menggeser nilai sebelumnya yang ditinggalkan oleh jumlah bit per karakter target, dan kemudian memasukkan pola bit karakter baru yang dipotong ke lebar target. karakter. Pola bit terakhir diberikan tipe int, dan karenanya ditandatangani, terlepas dari apakah karakter tunggal ditandatangani atau tidak.
Periksa penjelasannya di halaman ini untuk detail lebih lanjut
Mereka benar-benar hanya int
s. Mereka digunakan secara luas di Core Audio API enum misalnya, dalam CoreAudioTypes.h
file header,
enum
{
kAudioFormatLinearPCM = 'lpcm',
kAudioFormatAC3 = 'ac-3',
kAudioFormat60958AC3 = 'cac3',
kAudioFormatAppleIMA4 = 'ima4',
kAudioFormatMPEG4AAC = 'aac ',
kAudioFormatMPEG4CELP = 'celp',
} ;
Ada banyak obrolan tentang ini tidak menjadi "platform independen", tetapi ketika Anda menggunakan api yang dibuat untuk platform tertentu, yang peduli tentang portabilitas. Memeriksa kesetaraan pada platform yang sama tidak akan pernah gagal. Ini enum
'd nilai lebih mudah dibaca dan mereka benar-benar berisi identitas mereka di nilai mereka , yang cukup bagus.
Apa yang saya coba lakukan di bawah ini adalah membungkus karakter multibyte literal sehingga dapat dicetak (pada Mac ini berfungsi). Yang aneh adalah, jika Anda tidak menggunakan semua 4 karakter, hasilnya menjadi salah di bawah ini ..
#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;
}
Fitur semacam ini sangat bagus ketika Anda membuat parser. Pertimbangkan ini:
byte* buffer = ...;
if(*(int*)buffer == 'GET ')
invoke_get_method(buffer+4);
Kode ini kemungkinan hanya akan bekerja pada endianess tertentu dan mungkin menembus berbagai kompiler