Java整数からバイト配列


190

私は整数を得ました: 1695609641

私が方法を使うとき:

String hex = Integer.toHexString(1695609641);
system.out.println(hex); 

与える:

6510f329

しかし、バイト配列が必要です:

byte[] bytearray = new byte[] { (byte) 0x65, (byte)0x10, (byte)0xf3, (byte)0x29};

どうすればこれを作ることができますか?



回答:


293

Java NIOのByteBufferの使用は非常に簡単です。

byte[] bytes = ByteBuffer.allocate(4).putInt(1695609641).array();

for (byte b : bytes) {
   System.out.format("0x%x ", b);
}

出力:

0x65 0x10 0xf3 0x29 

4
または、"0x%02X"常に2つの16進数文字と大文字の16進数が必要な場合は、System.out.format("0x%02X", (byte) 10)displaysなどの形式を使用します0x0A
Maarten Bodewes、2012年

12
Integer.SIZE / 8を使用して、4などのLongのような他の型でうまく機能するパターンであるハードコーディングを回避できます。
davenpcj 2013年

3
@davenpcj Integer.SIZE / Byte.SIZEを使用することもできます
rkosegi

11
@rkosegiまたはJava 8以降のInteger.BYTES :)
drvdijk

1
@MaartenBodewesスレッドには、表示される書式設定はありませんが、ネイティブタイプの操作
Jacek Cz

146

どうですか:

public static final byte[] intToByteArray(int value) {
    return new byte[] {
            (byte)(value >>> 24),
            (byte)(value >>> 16),
            (byte)(value >>> 8),
            (byte)value};
}

アイデアはのものではありません。私はdzone.comのいくつかの投稿からそれを取っています。


44
私はあなたの要点を理解していますが、この特定のタスクでは、「私の」コードは「魔法の」ByteBufferよりも宣言的で明確です。
Grzegorz Oledzki、2010

24
@Kevin-それは非常に厳しいです-この種のコードが適切であるケースはたくさんあります、例えば画像処理において。JDKライブラリーは一般的に優れていますが、すべてのユースケースに対応しているわけではなく、最適化されていません。
mikera

14
同意した ByteBufferのオーバーヘッドと複雑さは、いくつかの単純でよく知られているバイト操作に比べて適切ではない場合があります。
swdunlop

6
追加するもう1つの点>>>は、右シフト演算子>>docs.oracle.com/javase/tutorial/java/nutsandbolts/op3.html)ではなく、符号なし右シフト演算子を使用したため、動作が期待どおりにならない可能性があります/符号付きの数値と符号なしの数値で予想通り
RobV

4
このアプローチは、前述のByteBufferまたはBigIntegerメソッドよりも少し速いようです。多くの変換を行う場合に考慮すべき他のこと。
シーカー、

45

BigInteger.valueOf(1695609641).toByteArray()


2
4バイトの配列を生成するという保証はありますか?
MeBigFatGuy 2013年

2
MeBigFatGuyが書いたとおりです。BigInteger.toByteArray()状態のJavadoc :「配列には、このBigIntegerを表すために必要な最小バイト数が含まれます...」
icza

2
質問のどこで、バイト配列を固定長4にするように求めますか?アルゴリズムによっては、これは配列の長さを利用できる一部であることを意味します
vmpn

これははるかに動的であり、正しい答えになるはずです。必要に応じて、配列の追加を行って希望のサイズを作成できます。特に、Javaの署名されたint値を考慮する必要がある場合。
ドロイドクリス

2
これは、0x7fに1バイト、0x80に2バイトを作成するようです(2バイトは0x0 0x80です)。
スコット2015

26
byte[] IntToByteArray( int data ) {    
    byte[] result = new byte[4];
    result[0] = (byte) ((data & 0xFF000000) >> 24);
    result[1] = (byte) ((data & 0x00FF0000) >> 16);
    result[2] = (byte) ((data & 0x0000FF00) >> 8);
    result[3] = (byte) ((data & 0x000000FF) >> 0);
    return result;        
}


7
byte[] conv = new byte[4];
conv[3] = (byte) input & 0xff;
input >>= 8;
conv[2] = (byte) input & 0xff;
input >>= 8;
conv[1] = (byte) input & 0xff;
input >>= 8;
conv[0] = (byte) input;

2
これにより、最下位の8バイトが抽出されます。また、入力数値の符号を変換されたオクテットにドラッグすることも回避します。
Carl Smotricz、2014年

stackoverflow.com/questions/35305634/…-このC#をJavaに解決できますか?

5
public static byte[] intToBytes(int x) throws IOException {
    ByteArrayOutputStream bos = new ByteArrayOutputStream();
    DataOutputStream out = new DataOutputStream(bos);
    out.writeInt(x);
    out.close();
    byte[] int_bytes = bos.toByteArray();
    bos.close();
    return int_bytes;
}

4

以下のチャンクは、少なくともUDPを介してintを送信するために機能します。

intからバイト配列へ:

public byte[] intToBytes(int my_int) throws IOException {
    ByteArrayOutputStream bos = new ByteArrayOutputStream();
    ObjectOutput out = new ObjectOutputStream(bos);
    out.writeInt(my_int);
    out.close();
    byte[] int_bytes = bos.toByteArray();
    bos.close();
    return int_bytes;
}

intへのバイト配列:

public int bytesToInt(byte[] int_bytes) throws IOException {
    ByteArrayInputStream bis = new ByteArrayInputStream(int_bytes);
    ObjectInputStream ois = new ObjectInputStream(bis);
    int my_int = ois.readInt();
    ois.close();
    return my_int;
}

4
ObjectOutputStreamの使用は正しくありません。DataOutputStreamを使用します。OOSを使用すると、バイト配列が4バイトになりません。
MeBigFatGuy 2013年

2

通常、この配列を後でintに変換する必要があるため、intの配列をバイトの配列に、またはその逆に変換するメソッドを次に示します。

public static byte[] convertToByteArray(final int[] pIntArray)
{
    final byte[] array = new byte[pIntArray.length * 4];
    for (int j = 0; j < pIntArray.length; j++)
    {
        final int c = pIntArray[j];
        array[j * 4] = (byte)((c & 0xFF000000) >> 24);
        array[j * 4 + 1] = (byte)((c & 0xFF0000) >> 16);
        array[j * 4 + 2] = (byte)((c & 0xFF00) >> 8);
        array[j * 4 + 3] = (byte)(c & 0xFF);
    }
    return array;
}

public static int[] convertToIntArray(final byte[] pByteArray)
{
    final int[] array = new int[pByteArray.length / 4];
    for (int i = 0; i < array.length; i++)
        array[i] = (((int)(pByteArray[i * 4]) << 24) & 0xFF000000) |
                (((int)(pByteArray[i * 4 + 1]) << 16) & 0xFF0000) |
                (((int)(pByteArray[i * 4 + 2]) << 8) & 0xFF00) |
                ((int)(pByteArray[i * 4 + 3]) & 0xFF);
    return array;
}

符号の伝播などのため、intに戻すときに「&0xFF ...」が必要であることに注意してください。


1
integer & 0xFF

最初のバイト

(integer >> 8) & 0xFF

2番目のループなどでは、事前に割り当てられたバイト配列に書き込みます。残念ながら少し厄介です。


1

クラスorg.apache.hadoop.hbase.util.Bytesには便利なbyte []変換メソッドがたくさんありますが、この目的のためだけにHBase jar全体をプロジェクトに追加したくない場合があります。そのようなメソッドがJDKか​​らAFAIKだけでなく、commons ioのような明らかなライブラリからも欠けているのは驚くべきことです。


1

私の試み:

public static byte[] toBytes(final int intVal, final int... intArray) {
    if (intArray == null || (intArray.length == 0)) {
        return ByteBuffer.allocate(4).putInt(intVal).array();
    } else {
        final ByteBuffer bb = ByteBuffer.allocate(4 + (intArray.length * 4)).putInt(intVal);
        for (final int val : intArray) {
            bb.putInt(val);
        }
        return bb.array();
    }
}

それでこれを行うことができます:

byte[] fourBytes = toBytes(0x01020304);
byte[] eightBytes = toBytes(0x01020304, 0x05060708);

完全なクラスはここにあります:https : //gist.github.com/superbob/6548493、それはshortsまたはlongからの初期化をサポートしています

byte[] eightBytesAgain = toBytes(0x0102030405060708L);

1

Apache Commonsを使用している場合

public static byte[] toByteArray(int value) {
    byte result[] = new byte[4];
    return Conversion.intToByteArray(value, 0, result, 0, 4);
}
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.