little-endian java_Little-Endian的JAVA
展開全部
JAVA字節(jié)序
BIG-ENDIAN、LITTLE-ENDIAN跟多字節(jié)類型的數(shù)據(jù)有關(guān)32313133353236313431303231363533e4b893e5b19e31333361303032,比如int,short,long型,而對單字節(jié)數(shù)據(jù)byte卻沒有影響。BIG-ENDIAN就是低位字節(jié)排放在內(nèi)存的高端,高位字節(jié)排放在內(nèi)存的低端。而LITTLE-ENDIAN正好相反。
比如 int a = 0x05060708
在BIG-ENDIAN的情況下存放為:
字節(jié)號 0 1 2 3
數(shù)據(jù) 05 06 07 08
在LITTLE-ENDIAN的情況下存放為:
字節(jié)號 0 1 2 3
數(shù)據(jù) 08 07 06 05
BIG-ENDIAN、LITTLE-ENDIAN跟CPU有關(guān),每一種CPU不是BIG-ENDIAN就是LITTLE-ENDIAN。IA架構(gòu)的CPU中是Little-Endian,而PowerPC 、SPARC和Motorola處理器則是BIG-ENDIAN。這其實(shí)就是所謂的主機(jī)字節(jié)序。而網(wǎng)絡(luò)字節(jié)序是指數(shù)據(jù)在網(wǎng)絡(luò)上傳輸時(shí)是大頭還是小頭的,在Internet的網(wǎng)絡(luò)字節(jié)序是BIG-ENDIAN。所謂的JAVA字節(jié)序指的是在JAVA虛擬機(jī)中多字節(jié)類型數(shù)據(jù)的存放順序,JAVA字節(jié)序也是BIG-ENDIAN。
所以在用C/C++寫通信程序時(shí),在發(fā)送數(shù)據(jù)前務(wù)必用htonl和htons去把整型和短整型的數(shù)據(jù)進(jìn)行從主機(jī)字節(jié)序到網(wǎng)絡(luò)字節(jié)序的轉(zhuǎn)換,而接收數(shù)據(jù)后對于整型和短整型數(shù)據(jù)則必須調(diào)用ntohl和ntohs實(shí)現(xiàn)從網(wǎng)絡(luò)字節(jié)序到主機(jī)字節(jié)序的轉(zhuǎn)換。如果通信的一方是JAVA程序、一方是C/C++程序時(shí),則需要在C/C++一側(cè)使用以上幾個(gè)方法進(jìn)行字節(jié)序的轉(zhuǎn)換,而JAVA一側(cè),則不需要做任何處理,因?yàn)镴AVA字節(jié)序與網(wǎng)絡(luò)字節(jié)序都是BIG-ENDIAN,只要C/C++一側(cè)能正確進(jìn)行轉(zhuǎn)換即可(發(fā)送前從主機(jī)序到網(wǎng)絡(luò)序,接收時(shí)反變換)。如果通信的雙方都是JAVA,則根本不用考慮字節(jié)序的問題了。
如果網(wǎng)絡(luò)上全部是PowerPC,SPARC和Motorola CPU的主機(jī)那么不會(huì)出現(xiàn)任何問題,但由于實(shí)際存在大量的IA架構(gòu)的CPU,所以經(jīng)常出現(xiàn)數(shù)據(jù)傳輸錯(cuò)誤。
文章開頭所提出的問題,就是因?yàn)槌绦蜻\(yùn)行在X86架構(gòu)的PC SERVER上,發(fā)送數(shù)據(jù)的一端是用C實(shí)現(xiàn)的,接收一端是用JAVA實(shí)現(xiàn)的,而發(fā)送端在發(fā)送數(shù)據(jù)前未進(jìn)行從主機(jī)字節(jié)序到網(wǎng)絡(luò)字節(jié)序的轉(zhuǎn)換,這樣接收端接收到的是LITTLE-ENDIAN的數(shù)據(jù),數(shù)據(jù)解釋自然出錯(cuò)。
具體數(shù)據(jù)如下,實(shí)際發(fā)送的數(shù)據(jù)為23578
發(fā)送端發(fā)送數(shù)據(jù): 1A 5C
接收端接收到數(shù)據(jù)后,按BIG-ENDIAN進(jìn)行解釋具體數(shù)據(jù)是多少?你們自己去計(jì)算并比較吧!
===============================================================================================
Big Endian and Little Endian
談到字節(jié)序的問題,必然牽涉到兩大CPU派系。那就是Motorola的PowerPC系列CPU和Intel的x86系列CPU。PowerPC系列采用big endian方式存儲(chǔ)數(shù)據(jù),而x86系列則采用little endian方式存儲(chǔ)數(shù)據(jù)
為什么要注意字節(jié)序的問題呢?你可能這么問。當(dāng)然,如果你寫的程序只在單機(jī)環(huán)境下面運(yùn)行,并且不和別人的程序打交道,那么你完全可以忽略字節(jié)序的存在。但是,如果你的程序要跟別人的程序產(chǎn)生交互呢?尤其是當(dāng)你把你在微機(jī)上運(yùn)算的結(jié)果運(yùn)用到計(jì)算機(jī)群上去的話。在這里我想說說兩種語言。C/C++語言編寫的程序里數(shù)據(jù)存儲(chǔ)順序是跟編譯平臺(tái)所在的CPU相關(guān)的,而JAVA編寫的程序則唯一采用big endian方式來存儲(chǔ)數(shù)據(jù)。試想,如果你用C/C++語言在x86平臺(tái)下編寫的程序跟別人的JAVA程序互通時(shí)會(huì)產(chǎn)生什么結(jié)果?就拿上面的 0x12345678來說,你的程序傳遞給別人的一個(gè)數(shù)據(jù),將指向0x12345678的指針傳給了JAVA程序,由于JAVA采取big endian方式存儲(chǔ)數(shù)據(jù),很自然的它會(huì)將你的數(shù)據(jù)翻譯為0x8765431。什么?竟然變成另外一個(gè)數(shù)字了?是的,就是這種后果。因此,在你的C程序傳給JAVA程序之前有必要進(jìn)行字節(jié)序的轉(zhuǎn)換工作。
Big-Endian和Little-Endian優(yōu)缺點(diǎn)
Big-Endian優(yōu)點(diǎn):靠首先提取高位字節(jié),你總是可以由看看在偏移位置為0的字節(jié)來確定這個(gè)數(shù)字是正數(shù)還是負(fù)數(shù)。你不必知道這個(gè)數(shù)值有多長,或者你也不必過一些字節(jié)來看這個(gè)數(shù)值是否含有符號位。這個(gè)數(shù)值是以它們被打印出來的順序存放的,所以從二進(jìn)制到十進(jìn)制的函數(shù)特別有效。因而,對于不同要求的機(jī)器,在設(shè)計(jì)存取方式時(shí)就會(huì)不同。
Little-Endian優(yōu)點(diǎn):提取一個(gè),兩個(gè),四個(gè)或者更長字節(jié)數(shù)據(jù)的匯編指令以與其他所有格式相同的方式進(jìn)行:首先在偏移地址為0的地方提取最低位的字節(jié),因?yàn)榈刂菲坪妥止?jié)數(shù)是一對一的關(guān)系,多重精度的數(shù)學(xué)函數(shù)就相對地容易寫了。
如果你增加數(shù)字的值,你可能在左邊增加數(shù)字(高位非指數(shù)函數(shù)需要更多的數(shù)字)。因此,經(jīng)常需要增加兩位數(shù)字并移動(dòng)存儲(chǔ)器里所有Big-endian順序的數(shù)字,把所有數(shù)向右移,這會(huì)增加計(jì)算機(jī)的工作量。不過,使用Little- Endian的存儲(chǔ)器中不重要的字節(jié)可以存在它原來的位置,新的數(shù)可以存在它的右邊的高位地址里。這就意味著計(jì)算機(jī)中的某些計(jì)算可以變得更加簡單和快速。
總結(jié)
以上是生活随笔為你收集整理的little-endian java_Little-Endian的JAVA的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: H7N9?生活还得继续~~适合边玩边学的
- 下一篇: URL长链转短链