2012-10-31 31 views
8
  1. 我想在Java中將字節轉換爲int。 我想假設字節爲無符號字節。 假設如果在java中將3個字節轉換爲int

    byte a = (byte)0xFF; 
    
    int r = (some operation on byte a); 
    

    r應該是255而不是十進制的-1。

  2. 然後,我想從3個字節創建int值。 假設如果

    byte b1 = (byte)0x0F; 
    
    byte b2 = (byte)0xFF; 
    
    byte b3 = (byte)0xFF; 
    
    int r = (some operation in bytes b1, b2 and b3); 
    

    則R應該是0x000FFFFF。字節b1將被放置在較高的第三位置,而字節b3將被放置在較低的第一位置。假設字節的無符號性,我的b1的範圍從0x00到0x0F,其他字節將從0x000xFF。如果字節b1大於0x0F,我將只提取最低4位。簡而言之,我想從3個字節中提取int,但只使用3個字節的20位。 (來自b2和b3的總共16個比特,以及來自b1的最低4個比特)。 int r必須是正數,因爲我們從3個字節創建並假定字節的無符號性質。

回答

3

你必須要小心的符號擴展在這裏 - 不幸的是,字節在Java中,據我所知籤(這已引起只是悲傷)。

所以你必須做一些掩蔽。

int r = (b3 & 0xFF) | ((b2 & 0xFF) << 8) | ((b1 & 0x0F) << 16); 
+0

感謝哈羅德,我得到正確的答案與您的解決方案。請解釋爲什麼逆序,我的意思是從上面的b1開始,它給我32640,這就是@ppeterka發佈的解決方案。 – UDPLover

+0

@ user1508907順序並不重要,但是ppeterka的回答可能會比'<<'更強烈地用'+'綁定。 – harold

+0

是的,我明白了。 ppeteka不使用括號。由於運營商的優先規則,解決方案陷入困境 – UDPLover

1

這裏的一個「僅移動」版本:

int r = ((b1 << 28) >>> 12) | (b2 << 8) | b3; 

左移28位扒關閉頂部4位,那麼右移12帶來回淨16位左移位。

我測試此代碼,它的工作原理:)

+0

你能解釋一下你所期望的過度轉移來實現呢? –

+0

哇,移動36位,砍掉頂部4位:) Eeeeevil :)我喜歡這樣!很高興每天都能學到東西! – ppeterka

+0

這將簽署延長第20位。如果你不希望你可以使用'>>>' –

2

這是很容易與bitshifting運營商,以及二進制和。你只想使用b1的低4位,這正是b1 & 0x0F所做的。所有剩下的就是移位比特到各種位置

int r = ((b1 & 0x0F) << 16) + ((b2 & 0xFF) << 8) + (b3 & 0xFF) 

EDIT作爲@harold指出的那樣,前一種溶液(不在下字節0xFF的掩模)會導致由於符號擴展異常.. 。

EDIT2天哪,我總是在臉上的運算符優先級與這些打交道時,打孔......

推薦閱讀:

+0

廢話,非常真實!馬上更新 – ppeterka

+0

我上面試過 - public class main { public static void main(String [ ]參數){ 字節B1 =(字節)爲0x0F; 字節B2 =(字節)0xff的; 字節B3 =(字節)0xff的; INT R =(B1&爲0x0F << 16)+(B2&0xFF的)<< 8 +(b3&0xFF); //打印 - r:32640 //我要r:1048575 System.out.println(「r:」+ r); } } 它給我32640,我想1048575 – UDPLover

+0

謝謝,但你的解決方案是錯誤的。當我從b3而不是b1開始時,它按照哈羅德給我正確的答案。使用你的解決方案給我32640,我想要1048575. – UDPLover

3

我會假設你想無符號字節值

int r = ((b1 & 0xF) << 16) | ((b2 & 0xFF) << 8) | (b3 & 0xFF); 

每個字節需要被掩蓋和右移位。

+1

這是正確的解決方案。謝謝 – UDPLover

0

我比較了一些答案,因爲我很好奇哪一個是最快的。

似乎波希米亞的方法是最快的,但我不能解釋爲什麼它在第一次運行中慢了11%。

PS .:我沒有檢查答案的正確性。

下面的代碼:

public class Test 
{ 

    public static void main(String[] args) 
    { 
    final int RUNS = 10; 
    final int TRIPLE = 3; 
    final int N = 100000000; 

    byte[] bytes = new byte[TRIPLE * 32768]; // 96 kB 

    Random r = new Random(); 
    r.nextBytes(bytes); 

    List<ByteConvertTester> testers = Arrays.asList(new Harold(), new Bohemian(), new Ppeterka()); 

    for (int i = 0; i < RUNS; i++) 
    { 
     System.out.println("RUN#" + i); 
     System.out.println("----------------------"); 
     Integer compare = null; 
     for (ByteConvertTester tester : testers) 
     { 
     System.out.println(tester.getClass().getSimpleName()); 
     long time = testAndMeasure(tester, bytes, N); 
     System.out.print("time (in ms): " + time); 
     if (compare != null) { 
      System.out.println(" SpeedUp%: " + (double) ((int) (10000 * (1.0d - (double) time/compare)))/100); 
     } else { 
      compare = (int) time; 
      System.out.println(); 
     } 
     } 
     System.out.println("----------------------"); 
    } 
    } 

    private static long testAndMeasure(ByteConvertTester bct, byte[] bytes, int loops) 
    { 
    Calendar start = Calendar.getInstance(); 
    int r; 
    for (int i = 0; i < loops; i += 3) 
     r = bct.test(bytes[i % bytes.length], bytes[(i + 1) % bytes.length], bytes[(i + 2) % bytes.length]); 

    Calendar end = Calendar.getInstance(); 
    long time = (end.getTimeInMillis() - start.getTimeInMillis()); 
    return time; 
    } 
} 

interface ByteConvertTester 
{ 
    public int test(byte msb, byte mid, byte lsb); 
} 

class Harold implements ByteConvertTester 
{ 
    @Override 
    public int test(byte msb, byte mid, byte lsb) 
    { 
    return (lsb & 0xFF) | ((mid & 0xFF) << 8) | ((msb & 0x0F) << 16); 
    } 
} 

class Bohemian implements ByteConvertTester 
{ 
    @Override 
    public int test(byte msb, byte mid, byte lsb) 
    { 
    return ((msb << 28) >>> 12) | (mid << 8) | lsb; 
    } 
} 

class Ppeterka implements ByteConvertTester 
{ 

    @Override 
    public int test(byte msb, byte mid, byte lsb) 
    { 
    return ((msb & 0x0F) << 16) + ((mid & 0xFF) << 8) + (lsb & 0xFF); 
    } 
} 

輸出

RUN#0 
---------------------- 
Harold 
time (in ms): 489 
Bohemian 
time (in ms): 547 SpeedUp%: -11.86 
Ppeterka 
time (in ms): 479 SpeedUp%: 2.04 
---------------------- 
RUN#1 
---------------------- 
Harold 
time (in ms): 531 
Bohemian 
time (in ms): 521 SpeedUp%: 1.88 
Ppeterka 
time (in ms): 537 SpeedUp%: -1.12 
---------------------- 
RUN#2 
---------------------- 
Harold 
time (in ms): 531 
Bohemian 
time (in ms): 539 SpeedUp%: -1.5 
Ppeterka 
time (in ms): 532 SpeedUp%: -0.18 
---------------------- 
RUN#3 
---------------------- 
Harold 
time (in ms): 529 
Bohemian 
time (in ms): 519 SpeedUp%: 1.89 
Ppeterka 
time (in ms): 531 SpeedUp%: -0.37 
---------------------- 
RUN#4 
---------------------- 
Harold 
time (in ms): 527 
Bohemian 
time (in ms): 519 SpeedUp%: 1.51 
Ppeterka 
time (in ms): 530 SpeedUp%: -0.56 
---------------------- 
RUN#5 
---------------------- 
Harold 
time (in ms): 528 
Bohemian 
time (in ms): 519 SpeedUp%: 1.7 
Ppeterka 
time (in ms): 532 SpeedUp%: -0.75 
---------------------- 
RUN#6 
---------------------- 
Harold 
time (in ms): 529 
Bohemian 
time (in ms): 520 SpeedUp%: 1.7 
Ppeterka 
time (in ms): 532 SpeedUp%: -0.56 
---------------------- 
RUN#7 
---------------------- 
Harold 
time (in ms): 529 
Bohemian 
time (in ms): 520 SpeedUp%: 1.7 
Ppeterka 
time (in ms): 533 SpeedUp%: -0.75 
---------------------- 
RUN#8 
---------------------- 
Harold 
time (in ms): 530 
Bohemian 
time (in ms): 521 SpeedUp%: 1.69 
Ppeterka 
time (in ms): 532 SpeedUp%: -0.37 
---------------------- 
RUN#9 
---------------------- 
Harold 
time (in ms): 529 
Bohemian 
time (in ms): 527 SpeedUp%: 0.37 
Ppeterka 
time (in ms): 530 SpeedUp%: -0.18 
----------------------