Javaを使用して、16進ダンプの文字列表現をバイト配列に変換しますか?


372

16進数値をバイト配列に表す(ダンプからの)長い文字列を変換する方法を探しています。

ここに同じ質問を投稿し人よりも上手に言い表せなかったでしょう。

しかし、元の状態を維持するために、私はそれを独自の方法で表現します。たとえば"00A0BF"、次のように解釈したい文字列があるとします

byte[] {0x00,0xA0,0xBf}

私は何をすべきか?

私はJavaの初心者で、最終BigInteger的に16進数のゼロを使用して監視していました。しかし、私はそれは醜いと思います、そして私は私が単純な何かを見逃していると確信しています。


stackoverflow.com/questions/9655181/…も参照してください。
flow2k 2018年

私はBigInteger ここで飼いならされました
ジョンマック

FWIW String.getBytes()は思ったように動作しません。これを難しい方法で学ばなければなりませんでした。if ("FF".getBytes() != "ff".getBytes()) { System.out.println("Try again"); }
tir38

回答:


636

これが、これまでに投稿されたどのソリューションよりも優れていると思う解決策です。

public static byte[] hexStringToByteArray(String s) {
    int len = s.length();
    byte[] data = new byte[len / 2];
    for (int i = 0; i < len; i += 2) {
        data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
                             + Character.digit(s.charAt(i+1), 16));
    }
    return data;
}

それが改善である理由:

  • 先行ゼロ(BigIntegerとは異なります)および負のバイト値(Byte.parseByteとは異なります)で安全

  • Stringをに変換したり、char[]1バイトごとにStringBuilderおよびStringオブジェクトを作成したりしません。

  • 使用できない可能性があるライブラリの依存関係はありません

assert引数が安全であることがわかっていない場合は、引数のチェックまたは例外を自由に追加してください。


2
正しくデコードされない例を挙げたり、それがどのように間違っているのか説明したりできますか?
デイブ・L

5
文字列「0」では機能しません。java.lang.StringIndexOutOfBoundsException
ovdsrnを

49
「0」は無効な入力です。バイトには、それぞれ2つの16進数が必要です。回答のメモにあるように、「引数の確認が安全かどうかわからない場合は、自由に引数チェックを追加してください。」
デイブL.

12
javax.xml.bind.DatatypeConverter.parseHexBinary(hexString)は、私のマイクロテストでの上記のソリューションよりも約20%高速であるように見え(価値のあるものは何でも)、無効な入力(たとえば "gg")で例外を正しくスローします。は有効なhexStringではありませんが、提案されたソリューションを使用して-77を返します。
Trevor Freeman

6
@DaedalusAlphaそれはあなたのコンテキストに依存しますが、通常、私は誤って間違ったデータを返すのではなく、仮定を修正できるように、そのようなことで速く大声で失敗する方が良いと思います。
Dave L.

331

ワンライナー:

import javax.xml.bind.DatatypeConverter;

public static String toHexString(byte[] array) {
    return DatatypeConverter.printHexBinary(array);
}

public static byte[] toByteArray(String s) {
    return DatatypeConverter.parseHexBinary(s);
}

警告

  • Java 9ジグソーでは、これは(デフォルト)java.seルートセットの一部ではないため、--add-modules java.se.eeを指定しない限り、ClassNotFoundExceptionが発生します(@に感謝eckes)。
  • Androidでは利用できません(これをFabian指摘してくれてありがとう)。ただし、システムになんらかの理由で不足している場合は、ソースコードを取得できますjavax.xmlBert Regelinkソースを抽出してくれた@ に感謝します。

14
私見これは(@DaveLの回答とは異なり)短くてすっきりしていて、外部ライブラリ(スカフマンの回答のような)を必要としないため、これは受け入れられた/トップの回答になるはずです。また、<自転車の再発明について身に着けた冗談を入力してください>
Priidu Neemre 2015

9
たとえば、datatypeconverterクラスはAndroidでは使用できません。
Fabian

4
警告:Java 9 Jigsawでは、これは(デフォルトの)java.seルートセットの一部ではないため、ClassNotFoundException指定しない限り、結果として--add-modules java.se.ee
eckes

2
@dantebarba私はjavax.xml.bind.DatatypeConverterすでにBase64データをエンコード/デコードする方法を提供していると思います。parseBase64Binary()およびを参照してくださいprintBase64Binary()
DragShot 2017

2
の問題に追加するためDataTypeConverter、Java SE 11はJAXB APIを完全に削除し、Java EEにのみ含まれるようになりました。ここで提案のようにしても、Mavenの依存関係として追加することができますstackoverflow.com/a/43574427/7347751
デヴィッドMordigal

79

commons-codecのHexクラスがそれを行うはずです。

http://commons.apache.org/codec/

import org.apache.commons.codec.binary.Hex;
...
byte[] decoded = Hex.decodeHex("00A0BF");
// 0x00 0xA0 0xBF

6
これもよさそうです。org.apache.commons.codec.binary.Hex.decodeHex()を参照してください
デイブL.

興味深かった。しかし、私は彼らの解決策に従うのが難しいと感じました。それはあなたが提案したものよりも利点がありますか(偶数の文字をチェックすること以外)
rafraf 2008

38

これで、BaseEncodingを使用しguavaてこれを実現できます。

BaseEncoding.base16().decode(string);

それを逆にするには

BaseEncoding.base16().encode(bytes);

27

実際、BigInteger is solutionは非常に優れていると思います。

new BigInteger("00A0BF", 16).toByteArray();

編集:ポスターで指摘されているように、先行ゼロは安全ではありません


私も最初はそう思っていました。そして、それを文書化してくれてありがとう-私は私がすべきだと思っていました...私が本当に理解していないけれども、それはいくつかの奇妙なことをしました遊んでいた。
rafraf 2008

2
これは、先頭の0についての良い点です。私はそれがバイトの順序を混同する可能性があると確信していません、そしてそれが実証されるのを見て非常に興味があります。
Dave L.

1
ええ、それを言ってもすぐには信じられませんでした:) BigIntegerのバイト配列とmmyers'fromHexStringを比較し、(0x00を使用せずに)問題の文字列と比較しました-それらは同一でした。「取り違え」は起こりましたが、それは別のことだったのかもしれません。明日はもっとよく見る
rafraf 2008

3
BigIntegerの問題は、「符号ビット」がなければならないことです。先頭バイトに上位ビットが設定されている場合、結果のバイト配列の最初の位置に余分な0があります。しかし、まだ+1。
2010年

25

ワンライナー:

import javax.xml.bind.DatatypeConverter;

public static String toHexString(byte[] array) {
    return DatatypeConverter.printHexBinary(array);
}

public static byte[] toByteArray(String s) {
    return DatatypeConverter.parseHexBinary(s);
}

背後にある実際のコードに興味を持ってあなたのそれらのためのワンライナーからFractalizeR(私はjavax.xml.bindの()は、デフォルトではAndroidのために利用可能ではないのでことを必要に応じて)、これはから来てcom.sun.xml.internal.bind。 DatatypeConverterImpl.java

public byte[] parseHexBinary(String s) {
    final int len = s.length();

    // "111" is not a valid hex encoding.
    if( len%2 != 0 )
        throw new IllegalArgumentException("hexBinary needs to be even-length: "+s);

    byte[] out = new byte[len/2];

    for( int i=0; i<len; i+=2 ) {
        int h = hexToBin(s.charAt(i  ));
        int l = hexToBin(s.charAt(i+1));
        if( h==-1 || l==-1 )
            throw new IllegalArgumentException("contains illegal character for hexBinary: "+s);

        out[i/2] = (byte)(h*16+l);
    }

    return out;
}

private static int hexToBin( char ch ) {
    if( '0'<=ch && ch<='9' )    return ch-'0';
    if( 'A'<=ch && ch<='F' )    return ch-'A'+10;
    if( 'a'<=ch && ch<='f' )    return ch-'a'+10;
    return -1;
}

private static final char[] hexCode = "0123456789ABCDEF".toCharArray();

public String printHexBinary(byte[] data) {
    StringBuilder r = new StringBuilder(data.length*2);
    for ( byte b : data) {
        r.append(hexCode[(b >> 4) & 0xF]);
        r.append(hexCode[(b & 0xF)]);
    }
    return r.toString();
}

3
DatatypeConverterは、Java 9でもデフォルトでは使用できません。危険なのは、それを使用するコードがJava 1.8以前(ソース設定が以前のJava 9)でコンパイルされるが、「-add-modules java.se.ee」なしでJava 9でランタイム例外が発生することです。
スティーブンM-ストライキ-2017

24

HexBinaryAdapter間のマーシャルとアンマーシャリングする機能を提供Stringしてしbyte[]

import javax.xml.bind.annotation.adapters.HexBinaryAdapter;

public byte[] hexToBytes(String hexString) {
     HexBinaryAdapter adapter = new HexBinaryAdapter();
     byte[] bytes = adapter.unmarshal(hexString);
     return bytes;
}

それは私が入力した例にすぎません...実際にはそのまま使用するだけで、それを使用するための個別のメソッドを作成する必要はありません。


5
入力文字列(hexString)の文字数が偶数の場合にのみ機能します。それ以外の場合:スレッド "main"の例外java.lang.IllegalArgumentException:hexBinaryは偶数の長さである必要があります:
ovdsrn

3
ああ、指摘してくれてありがとう。バイト配列は{0x00,0xA0,0xBf}として表されるため、ユーザーには実際には奇数の文字は必要ありません。各バイトには2桁の16進数またはニブルがあります。したがって、バイト数は常に偶数文字にする必要があります。これについて言及していただきありがとうございます。
GrkEngineer 2011年

8
HexBinaryAdapter(DatatypeConverterを呼び出す)を使用する代わりに、java.xml.bind.DatatypeConverter.parseHexBinary(hexString)を直接使用できます。これにより、アダプターインスタンスオブジェクトを作成する必要がなくなります(DatatypeConverterメソッドは静的であるため)。
Trevor Freeman

。javax.xml.bindの*危険な事は、それは、Java 1.8またはそれ以前(それ以前に元の設定でJava 9)の下でコンパイルしますが、Java 9の下で実行されているランタイム例外が発生します使用してコードであるJavaの9に利用できなくなりました
スティーブンM-ストライキ-2017

15

実際に機能する方法は次のとおりです(以前のいくつかの半正解に基づく)。

private static byte[] fromHexString(final String encoded) {
    if ((encoded.length() % 2) != 0)
        throw new IllegalArgumentException("Input string must contain an even number of characters");

    final byte result[] = new byte[encoded.length()/2];
    final char enc[] = encoded.toCharArray();
    for (int i = 0; i < enc.length; i += 2) {
        StringBuilder curr = new StringBuilder(2);
        curr.append(enc[i]).append(enc[i + 1]);
        result[i/2] = (byte) Integer.parseInt(curr.toString(), 16);
    }
    return result;
}

私が見ることができる唯一の考えられる問題は、入力文字列が極端に長い場合です。toCharArray()を呼び出すと、文字列の内部配列のコピーが作成されます。

編集:ああ、ところで、バイトはJavaで署名されているので、入力文字列は[0、160、191]ではなく[0、-96、-65]に変換されます。しかし、おそらくあなたはすでにそれを知っていました。


1
ありがとうマイケル-あなたは命の恩人です!BlackBerryプロジェクトで作業し、RIMの「Byte.parseByte(byteString、16)」メソッドを使用して、バイトの文字列表現をバイトに変換しようとしています... NumberFormatExcpetionをスローし続けました。理由を理解するために疲れる時間を費やしました。あなたの「Integer.praseInt()」の提案はトリックをしました。再度、感謝します!!
BonanzaDriver 2011年

12

Androidでは、16進数で作業している場合は、okioを試すことができます

簡単な使い方:

byte[] bytes = ByteString.decodeHex("c000060000").toByteArray();

そして結果は

[-64, 0, 6, 0, 0]

私は多くの異なる方法をテストしましたが、これは少なくとも2倍の速さです!
poby

5

BigInteger()java.math のメソッドは非常に遅く、推奨できません。

Integer.parseInt(HEXString, 16)

Digit / Integerに変換せずに一部の文字で問題が発生する可能性があります

よく働く方法:

Integer.decode("0xXX") .byteValue()

関数:

public static byte[] HexStringToByteArray(String s) {
    byte data[] = new byte[s.length()/2];
    for(int i=0;i < s.length();i+=2) {
        data[i/2] = (Integer.decode("0x"+s.charAt(i)+s.charAt(i+1))).byteValue();
    }
    return data;
}

楽しい、幸運を


4

編集:@mmyersによって指摘されているように、このメソッドは、高ビットセット( "80"-"FF")のバイトに対応する部分文字列を含む入力に対しては機能しません。説明は、バグID:6259307 Byte.parseByteがSDKドキュメントで宣伝されているように機能しない場合です。

public static final byte[] fromHexString(final String s) {
    byte[] arr = new byte[s.length()/2];
    for ( int start = 0; start < s.length(); start += 2 )
    {
        String thisByte = s.substring(start, start+2);
        arr[start/2] = Byte.parseByte(thisByte, 16);
    }
    return arr;
}

1
閉じるが、このメソッドは指定された入力「00A0BBF」で失敗します。bugs.sun.com/bugdatabase/view_bug.do?bug_id=6259307を参照してください。
マイケルマイヤーズ

1
また、奇妙なことに「9C」に対応していません
rafraf

1
@mmyers:おっと。それは良いことではありません。混乱してごめんなさい。@ravigad:この場合、上位ビットが設定されているため、9Cにも同じ問題があります。
ブレアコンラッド

(byte)Short.parseShort(thisByte、16)はその問題を解決します
Jamey Hicks

3

価値のあるものとして、文字列の連結に頼らずに奇数長の文字列をサポートする別のバージョンを次に示します。

public static byte[] hexStringToByteArray(String input) {
    int len = input.length();

    if (len == 0) {
        return new byte[] {};
    }

    byte[] data;
    int startIdx;
    if (len % 2 != 0) {
        data = new byte[(len / 2) + 1];
        data[0] = (byte) Character.digit(input.charAt(0), 16);
        startIdx = 1;
    } else {
        data = new byte[len / 2];
        startIdx = 0;
    }

    for (int i = startIdx; i < len; i += 2) {
        data[(i + 1) / 2] = (byte) ((Character.digit(input.charAt(i), 16) << 4)
                + Character.digit(input.charAt(i+1), 16));
    }
    return data;
}

2

私はいつものような方法を使用してきました

public static final byte[] fromHexString(final String s) {
    String[] v = s.split(" ");
    byte[] arr = new byte[v.length];
    int i = 0;
    for(String val: v) {
        arr[i++] =  Integer.decode("0x" + val).byteValue();

    }
    return arr;
}

このメソッドは、スペースで区切られた16進値で分割しますが、2つの文字のグループなど、他の基準で文字列を分割することは難しくありません。


文字列の連結は不要です。Integer.valueOf(val、16)を使用してください。
マイケルマイヤーズ

以前にそのような基数変換を使用してみましたが、結果はまちまちです
pfranza

おかげで-奇妙なことに、この文字列「9C001C」または「001C21」で正常に動作し、次の文字列で失敗します:「9C001C21」スレッド「メイン」の例外java.lang.NumberFormatException:入力文字列の場合:java.langの「9C001C21」 NumberFormatException.forInputString(Unknown Source)
rafraf

(これはByte/ byteケースよりも奇妙なことではありません:先行ビットなしで設定された最高のビット-)
greybeard

2

私はCharacter.digitソリューションが好きですが、これは私がそれをどのように解決したかです

public byte[] hex2ByteArray( String hexString ) {
    String hexVal = "0123456789ABCDEF";
    byte[] out = new byte[hexString.length() / 2];

    int n = hexString.length();

    for( int i = 0; i < n; i += 2 ) {
        //make a bit representation in an int of the hex value 
        int hn = hexVal.indexOf( hexString.charAt( i ) );
        int ln = hexVal.indexOf( hexString.charAt( i + 1 ) );

        //now just shift the high order nibble and add them together
        out[i/2] = (byte)( ( hn << 4 ) | ln );
    }

    return out;
}

2

Bert Regelinkによって提示されたコードは単に機能しません。以下を試してください:

import javax.xml.bind.DatatypeConverter;
import java.io.*;

public class Test
{  
    @Test
    public void testObjectStreams( ) throws IOException, ClassNotFoundException
    {     
            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            ObjectOutputStream oos = new ObjectOutputStream(baos);

            String stringTest = "TEST";
            oos.writeObject( stringTest );

            oos.close();
            baos.close();

            byte[] bytes = baos.toByteArray();
            String hexString = DatatypeConverter.printHexBinary( bytes);
            byte[] reconvertedBytes = DatatypeConverter.parseHexBinary(hexString);

            assertArrayEquals( bytes, reconvertedBytes );

            ByteArrayInputStream bais = new ByteArrayInputStream(reconvertedBytes);
            ObjectInputStream ois = new ObjectInputStream(bais);

            String readString = (String) ois.readObject();

            assertEquals( stringTest, readString);
        }
    }

2
これは実際には別の問題であり、おそらく別のスレッドに属しています。
Sean Coffey

1

カーネルパニックが最も役立つ解決策であることがわかりましたが、16進文字列が奇数の場合、問題が発生しました。このように解決しました:

boolean isOdd(int value)
{
    return (value & 0x01) !=0;
}

private int hexToByte(byte[] out, int value)
{
    String hexVal = "0123456789ABCDEF"; 
    String hexValL = "0123456789abcdef";
    String st = Integer.toHexString(value);
    int len = st.length();
    if (isOdd(len))
        {
        len+=1; // need length to be an even number.
        st = ("0" + st);  // make it an even number of chars
        }
    out[0]=(byte)(len/2);
    for (int i =0;i<len;i+=2)
    {
        int hh = hexVal.indexOf(st.charAt(i));
            if (hh == -1)  hh = hexValL.indexOf(st.charAt(i));
        int lh = hexVal.indexOf(st.charAt(i+1));
            if (lh == -1)  lh = hexValL.indexOf(st.charAt(i+1));
        out[(i/2)+1] = (byte)((hh << 4)|lh);
    }
    return (len/2)+1;
}

配列に16進数の数を追加しているので、使用している配列への参照を渡し、変換する必要のある整数と次の16進数の相対位置を返します。したがって、最終的なバイト配列には、[0]の16進ペアの数、[1 ...]の16進ペア、次にペアの数...


1

op投票のソリューションに基づくと、次の方が少し効率的です。

  public static byte [] hexStringToByteArray (final String s) {
    if (s == null || (s.length () % 2) == 1)
      throw new IllegalArgumentException ();
    final char [] chars = s.toCharArray ();
    final int len = chars.length;
    final byte [] data = new byte [len / 2];
    for (int i = 0; i < len; i += 2) {
      data[i / 2] = (byte) ((Character.digit (chars[i], 16) << 4) + Character.digit (chars[i + 1], 16));
    }
    return data;
  }

理由:char配列への最初の変換により、charAtでの長さチェックが不要になります。


1

コーディングスタイルとしてJava 8ストリームを優先する場合、これはJDKプリミティブだけを使用して実現できます。

String hex = "0001027f80fdfeff";

byte[] converted = IntStream.range(0, hex.length() / 2)
    .map(i -> Character.digit(hex.charAt(i * 2), 16) << 4 | Character.digit(hex.charAt((i * 2) + 1), 16))
    .collect(ByteArrayOutputStream::new,
             ByteArrayOutputStream::write,
             (s1, s2) -> s1.write(s2.toByteArray(), 0, s2.size()))
    .toByteArray();

, 0, s2.size()キャッチしてもかまわない場合は、コレクター連結関数のパラメーターを省略できますIOException


0
public static byte[] hex2ba(String sHex) throws Hex2baException {
    if (1==sHex.length()%2) {
        throw(new Hex2baException("Hex string need even number of chars"));
    }

    byte[] ba = new byte[sHex.length()/2];
    for (int i=0;i<sHex.length()/2;i++) {
        ba[i] = (Integer.decode(
                "0x"+sHex.substring(i*2, (i+1)*2))).byteValue();
    }
    return ba;
}

0

私の正式な解決策:

/**
 * Decodes a hexadecimally encoded binary string.
 * <p>
 * Note that this function does <em>NOT</em> convert a hexadecimal number to a
 * binary number.
 *
 * @param hex Hexadecimal representation of data.
 * @return The byte[] representation of the given data.
 * @throws NumberFormatException If the hexadecimal input string is of odd
 * length or invalid hexadecimal string.
 */
public static byte[] hex2bin(String hex) throws NumberFormatException {
    if (hex.length() % 2 > 0) {
        throw new NumberFormatException("Hexadecimal input string must have an even length.");
    }
    byte[] r = new byte[hex.length() / 2];
    for (int i = hex.length(); i > 0;) {
        r[i / 2 - 1] = (byte) (digit(hex.charAt(--i)) | (digit(hex.charAt(--i)) << 4));
    }
    return r;
}

private static int digit(char ch) {
    int r = Character.digit(ch, 16);
    if (r < 0) {
        throw new NumberFormatException("Invalid hexadecimal string: " + ch);
    }
    return r;
}

PHP hex2bin()関数に似ていますが、Javaスタイルです。

例:

String data = new String(hex2bin("6578616d706c65206865782064617461"));
// data value: "example hex data"

0

パーティーに遅れましたが、私はDaveLによって上記の答えを逆のアクションを持つクラスに統合しました-万が一に備えて。

public final class HexString {
    private static final char[] digits = "0123456789ABCDEF".toCharArray();

    private HexString() {}

    public static final String fromBytes(final byte[] bytes) {
        final StringBuilder buf = new StringBuilder();
        for (int i = 0; i < bytes.length; i++) {
            buf.append(HexString.digits[(bytes[i] >> 4) & 0x0f]);
            buf.append(HexString.digits[bytes[i] & 0x0f]);
        }
        return buf.toString();
    }

    public static final byte[] toByteArray(final String hexString) {
        if ((hexString.length() % 2) != 0) {
            throw new IllegalArgumentException("Input string must contain an even number of characters");
        }
        final int len = hexString.length();
        final byte[] data = new byte[len / 2];
        for (int i = 0; i < len; i += 2) {
            data[i / 2] = (byte) ((Character.digit(hexString.charAt(i), 16) << 4)
                    + Character.digit(hexString.charAt(i + 1), 16));
        }
        return data;
    }
}

そしてJUnitテストクラス:

public class TestHexString {

    @Test
    public void test() {
        String[] tests = {"0FA1056D73", "", "00", "0123456789ABCDEF", "FFFFFFFF"};

        for (int i = 0; i < tests.length; i++) {
            String in = tests[i];
            byte[] bytes = HexString.toByteArray(in);
            String out = HexString.fromBytes(bytes);
            System.out.println(in); //DEBUG
            System.out.println(out); //DEBUG
            Assert.assertEquals(in, out);

        }

    }

}

0

私はこれが非常に古いスレッドであることを知っていますが、それでも私の価値を追加したいと思います。

バイナリコンバーターへの単純な16進文字列を実際にコーディングする必要がある場合は、次のようにしたいと思います。

public static byte[] hexToBinary(String s){

  /*
   * skipped any input validation code
   */

  byte[] data = new byte[s.length()/2];

  for( int i=0, j=0; 
       i<s.length() && j<data.length; 
       i+=2, j++)
  {
     data[j] = (byte)Integer.parseInt(s.substring(i, i+2), 16);
  }

  return data;
}

0

はるかにクリーンなソリューションではありません。しかし、それは私にとってはうまくいき、適切にフォーマットされています:

private String createHexDump(byte[] msg, String description) {
    System.out.println();
    String result = "\n" + description;
    int currentIndex = 0;
    int printedIndex = 0;
    for(int i=0 ; i<msg.length ; i++){
        currentIndex++;
        if(i == 0){
            result += String.format("\n  %04x ", i);
        }
        if(i % 16 == 0 && i != 0){
            result += " | ";
            for(int j=(i-16) ; j<msg.length && j<i ; j++) {
                char characterToAdd = (char) msg[j];
                if (characterToAdd == '\n') {
                    characterToAdd = ' ';
                }
                result += characterToAdd;
                printedIndex++;
            }

            result += String.format("\n  %04x ", i);
        }

        result += String.format("%02x ", msg[i]);
    }

    if(currentIndex - printedIndex > 0){
        int leftOvers = currentIndex - printedIndex;
        for(int i=0 ; i<16-leftOvers ; i++){
            result += "   ";
        }

        result += " | ";

        for(int i=msg.length-leftOvers ; i<msg.length ; i++){
            char characterToAdd = (char) msg[i];
            if (characterToAdd == '\n') {
                characterToAdd = ' ';
            }
            result += characterToAdd;
        }
    }

    result += "\n";

    return result;
}

出力:

  S -> C
    0000 0b 00 2e 06 4d 6f 72 69 74 7a 53 6f 6d 65 20 54  |  .Heyyy Some T
    0010 43 50 20 73 74 75 66 66 20 49 20 63 61 70 74 75  | CP stuff I captu
    0020 72 65 64 2e 2e 77 65 6c 6c 20 66 6f 72 6d 61 74  | red..well format
    0030 3f                                               | ?

-2

私はあなたのためにそれをやると思います。データを文字列として返す同様の関数からまとめました。

private static byte[] decode(String encoded) {
    byte result[] = new byte[encoded/2];
    char enc[] = encoded.toUpperCase().toCharArray();
    StringBuffer curr;
    for (int i = 0; i < enc.length; i += 2) {
        curr = new StringBuffer("");
        curr.append(String.valueOf(enc[i]));
        curr.append(String.valueOf(enc[i + 1]));
        result[i] = (byte) Integer.parseInt(curr.toString(), 16);
    }
    return result;
}

まず、文字列を大文字に変換する必要はありません。第二に、文字列をStringBufferに直接追加することが可能です。これははるかに効率的です。
マイケルマイヤーズ

-2

私にとってこれが解決策でした、HEX = "FF01"はFF(255)と01(01)に分割されます

private static byte[] BytesEncode(String encoded) {
    //System.out.println(encoded.length());
    byte result[] = new byte[encoded.length() / 2];
    char enc[] = encoded.toUpperCase().toCharArray();
    String curr = "";
    for (int i = 0; i < encoded.length(); i=i+2) {
        curr = encoded.substring(i,i+2);
        System.out.println(curr);
        if(i==0){
            result[i]=((byte) Integer.parseInt(curr, 16));
        }else{
            result[i/2]=((byte) Integer.parseInt(curr, 16));
        }

    }
    return result;
}

この質問はしばらくの間回答されており、適切な代替案がいくつかあります。残念ながら、あなたの答えはこの時点で大幅に改善された価値を提供していません。
rfornal
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.