Konvertiert einen string von hex-dump zu einem byte-array mithilfe von Java?
Ich bin auf der Suche nach einem Weg, um zu konvertieren eine lange Schnur (aus einem dump), das entspricht hex-Wert in ein byte-array.
Hätte ich nicht so formuliert es besser als die person, die gepostet die gleiche Frage hier.
Aber halten es original, ich werde die phrase, es auf meine eigene Art und Weise: angenommen ich habe einen string "00A0BF"
möchte ich interpretiert als die
byte[] {0x00,0xA0,0xBf}
was soll ich tun?
Ich bin ein Java-Anfänger und landete mit BigInteger
und gerade für führende hex-Nullen. Aber ich denke, es ist hässlich und ich bin sicher, ich bin etwas fehlt einfach.
InformationsquelleAutor rafraf | 2008-09-26
Du musst angemeldet sein, um einen Kommentar abzugeben.
Hier ist eine Lösung, die ich denke, ist besser als jeder gepostet so weit:
Gründe, warum es eine Verbesserung:
Sicher mit führenden Nullen (im Gegensatz zu BigInteger) und mit negativ-byte-Werte (im Gegensatz zu Byte.parseByte)
Nicht konvertieren Sie die Zeichenfolge in eine
char[]
oder erstellen StringBuilder und String-Objekte für jedes einzelne byte.Keine Bibliothek-Abhängigkeiten, die möglicherweise nicht verfügbar
Fühlen Sie sich frei, um eine überprüfung der Argumente über
assert
oder Ausnahmen, wenn das argument ist nicht bekannt, sicher zu sein.Es funktioniert nicht für den String "0". Es wirft eine java.lang.StringIndexOutOfBoundsException
"0" ist keine gültige Eingabe. Bytes erfordern zwei hexadezimalen Ziffern. Als "Antwort " Notizen", Fühlen Sie sich frei, um eine überprüfung der Argumente...wenn das argument ist nicht bekannt, sicher zu sein."
javax.xml.binden.DatatypeConverter.parseHexBinary(hexString) scheint zu sein, etwa 20% schneller als die oben genannte Lösung in meinem micro-Prüfungen (für was auch immer, dass Sie wenig Wert sind), sowie richtig throwing exceptions bei ungültigen Eingaben (z.B. "gg" ist keine gültige hexString aber zurück -77 verwenden Sie die Lösung, wie vorgeschlagen).
Es kommt auf den Kontext an, aber in der Regel finde ich es besser, zu scheitern, schnell und laut mit solchen Dingen, so dass Sie beheben können Ihre Annahmen anstatt schweigend Rücksendung fehlerhafter Daten.
InformationsquelleAutor Dave L.
Einzeiler:
Warnungen:
gesetzt also, es wird eine ClassNotFoundException, wenn Sie angeben,
--add-Module java.se.ee (Dank an @
eckes
)Fabian
für erwähnenswert, dass), aber Sie können nur nehmen Sie den source-code wenn Ihr system fehltjavax.xml
aus irgendeinem Grund. Dank @Bert Regelink
für das extrahieren der Quelle.die datatypeconverter Klasse ist nicht verfügbar in android zum Beispiel.
Achtung: in Java 9-Stichsäge dies ist nicht mehr Teil des (Standard -)
java.se
root gesetzt, so wird das Resultat in einerClassNotFoundException
es sei denn, Sie geben--add-modules java.se.ee
Erstaunliche Antwort, könnte decodiert einen base64-string anfordern, verwendet hex umwandeln byte-array mit den zur Verfügung gestellten Lösung und es funktionierte wie ein Charme
Ich denke
javax.xml.bind.DatatypeConverter
bietet bereits eine Methode zur Codierung/Decodierung von Base64-Daten. SehenparseBase64Binary()
undprintBase64Binary()
.InformationsquelleAutor Vladislav Rastrusny
Den Hex-Klasse in commons-codec sollte das für Sie tun.
http://commons.apache.org/codec/
Es war sehr interessant. Aber ich fand Ihre Lösung schwer zu Folgen. Gibt es irgendwelche Vorteile über das, was Sie vorgeschlagen (andere als die überprüfung für gerade Zahl von Zeichen)?
InformationsquelleAutor skaffman
Können Sie jetzt mit BaseEncoding in
guava
um dies zu erreichen.Rückgängig zu machen verwenden Sie
InformationsquelleAutor jontro
Eigentlich finde ich die BigInteger ist die Lösung sehr schön:
Edit: Nicht sicher für führende Nullen, wie bereits von dem Plakat.
Das ist ein guter Punkt, um führende 0. Ich bin mir nicht sicher, ich glaube, es könnte ein vertauschen der Reihenfolge von bytes, und wäre sehr daran interessiert zu sehen, es gezeigt.
ja, sobald ich es sagte, ich konnte nicht glauben, mir auch 🙂 ich lief ein vergleichen der byte-array von BigInteger mit mmyers'fromHexString und (mit keine 0x00) gegen die Verfügungen string - Sie waren identisch. Die "mix-up" geschehen, aber es darf schon was anderes. Ich willlook mehr eng morgen
Das Problem mit BigInteger ist, dass es ein "Vorzeichen-bit". Wenn das führende byte das höchste bit gesetzt ist, dann das resultierende byte-array hat eine zusätzliche 0 in der 1. position. Aber immer noch +1.
InformationsquelleAutor Dave L.
Den
HexBinaryAdapter
bietet die Möglichkeit, marshal und unmarshal zwischenString
undbyte[]
.Das ist nur ein Beispiel, das ich eingegeben...ich eigentlich nur benutzen und nicht brauchen, um eine separate Methode für die Verwendung.
Oh, danke für den Hinweis. Ein Benutzer sollte das wirklich nicht haben eine ungerade Anzahl von Zeichen, weil das byte-array wird dargestellt als {0x00,0xA0,0xBf}. Jedes byte hat zwei hex-Ziffern oder knabbert. Also eine beliebige Anzahl von bytes sollte immer eine gerade Anzahl von Zeichen. Vielen Dank für die Erwähnung.
Sie können die Verwendung von java.xml.binden.DatatypeConverter.parseHexBinary(hexString) direkt anstatt HexBinaryAdapter (die wiederum ruft DatatypeConverter). Diese Weise werden Sie nicht haben, um einen adapter-Instanz-Objekt (seit DatatypeConverter Methoden statisch sind).
javax.xml.binden.* ist nicht mehr verfügbar, in Java 9. Die gefährliche Sache ist der code dann kompilieren unter Java 1.8 oder früher (Java 9 mit der source-Einstellungen zu früher), aber eine Laufzeit-exception läuft unter Java 9.
InformationsquelleAutor GrkEngineer
Für diejenigen von Ihnen interessiert, die in den eigentlichen code hinter der Einzeiler von FractalizeR (brauchte ich, da javax.xml.binden ist nicht verfügbar für Android (standardmäßig)), das kommt von com.sun.xml.internal.bind.DatatypeConverterImpl.java :
InformationsquelleAutor Bert Regelink
Hier ist eine Methode, die tatsächlich funktioniert (basiert auf mehreren früheren halb-richtige Antworten):
Das einzige mögliche Problem, das ich sehen kann, wenn der input-string ist extrem lang; der Aufruf toCharArray() gibt eine Kopie des string s interne array.
EDIT: Oh, und übrigens, sind die bytes unterzeichnet in Java, so dass Ihr input-string konvertiert zu [0, -96, -65] anstelle von [0, 160, 191]. Aber Sie wusste wohl, dass bereits.
InformationsquelleAutor Michael Myers
In android ,wenn Sie mit hex, können Sie versuchen,okio.
einfache Nutzung:
und Ergebnis
InformationsquelleAutor Miao1007
EDIT: wie bereits von @mmyers, diese Methode funktioniert nicht auf Eingaben mit Teilstrings entsprechende Byte mit dem high-bit gesetzt ("80" - "FF"). Die Erklärung ist an Bug ID: 6259307 Byte.parseByte nicht wie beworben in der SDK-Dokumentation.
Auch seltsam es befasst sich nicht mit "9C"
boah. Das ist nicht gut. Sorry für th Verwirrung. @ravigad: 9C hat das gleiche problem, weil in diesem Fall die hohe bit gesetzt ist.
(byte)Kurz.parseShort(thisByte, 16) löst das problem
InformationsquelleAutor Blair Conrad
Den
BigInteger()
- Methode aus java.Mathe ist sehr Langsam und nicht empfehlenswert.Integer.parseInt(HEXString, 16)
kann Probleme verursachen, bei manchen Zeichen ohne
konvertieren zu Ziffern /Integer
als eine Gut Funktionierende Methode:
Funktion:
Spaß Haben, Viel Glück
InformationsquelleAutor Sniper
Den Code von Bert Regelink einfach nicht funktioniert.
Versuchen Sie Folgendes:
InformationsquelleAutor Sean Coffey
Für was es Wert ist, hier ist eine andere version, die unterstützt ungerade strings, ohne Rückgriff auf die string-Verkettung.
InformationsquelleAutor Conor Svensson
Habe ich immer eine Methode wie
diese Methode spaltet auf Leerzeichen als Trennzeichen hex-Werte, aber es wäre nicht schwer zu machen, teilen Sie die Zeichenfolge auf anderen Kriterien wie in Gruppierungen von zwei Zeichen.
Ich habe versucht, mit den radix-Konvertierungen, wie das vor und ich habe gemischte Ergebnisse
Meinst du, es falsch umgewandelt?
vielen Dank - seltsam, es funktioniert gut mit dieser Zeichenfolge: "9C001C" oder "001C21" und schlägt mit diesem einen: "9C001C21" Exception in thread "main" java.lang.NumberFormatException: For input string: "9C001C21" in java.lang.NumberFormatException.forInputString(Quelle Unbekannt)
(Das ist nicht merkwürdiger als in der
Byte
/byte
Fall: höchste bit gesetzt ohne führende -)InformationsquelleAutor pfranza
Ich mag den Charakter.Ziffer Lösung, aber hier ist, wie ich es gelöst
InformationsquelleAutor Kernel Panic
Fand ich Kernel Panic-die Lösung, die die meisten hilfreich für mich, aber lief in Probleme, wenn der hex-string eine ungerade Zahl. löste es auf diese Weise:
Ich bin das hinzufügen einer Anzahl von hex-zahlen in ein array, so dass ich übergeben Sie die Referenz auf das array, die ich verwende, und die int Brauch ich konvertiert und gibt die relative position des nächsten hex-Zahl. Also das Letzte byte array [0] Anzahl der hex-Paare, [1...] hex-Paare, dann die Anzahl der Paare...
InformationsquelleAutor Clayton Balabanov
Basiert auf dem op-Lösung gewählt, die folgende sollte ein bisschen effizienter:
Da: die erste Konvertierung in ein char-array schont die Länge geprüft charAt
InformationsquelleAutor Philip Helger
Wenn Sie haben eine Vorliebe für Java 8 streams als Ihre coding-Stil, dann kann dies erreicht werden, mit nur JDK primitiven.
Den
, 0, s2.size()
Parameter in der collector ' verketten-Funktion kann weggelassen werden, wenn Sie nichts dagegen haben, fangenIOException
.InformationsquelleAutor Andy Brown
InformationsquelleAutor David V
Meine formale Lösung:
Ist wie die PHP hex2bin () - Funktion, sondern in Java-Stil.
Beispiel:
InformationsquelleAutor Daniel De León
Bei weitem nicht die sauberste Lösung. Aber es funktioniert für mich und ist gut formatiert:
Die Ausgabe:
InformationsquelleAutor Moritz Schmidt
Spät zur party, aber ich habe eingemeindet, die Antwort oben von DaveL in eine Klasse mit umgekehrter Handlung - nur, falls es hilft.
- Und JUnit-test-Klasse:
InformationsquelleAutor DrPhill
Ich weiß, das ist ein sehr Alter thread, aber immer noch, wie meine penny Wert.
Wenn ich wirklich brauchen, um code einen einfachen hex-string in Binär-Konverter, möchte ich es wie folgt.
InformationsquelleAutor tigger
Denke ich, wird es für Sie tun. Ich gepflasterten es zusammen aus einer ähnlichen Funktion, dass die Daten zurückgegeben, als ein string:
InformationsquelleAutor Bob King
War dies für Mich die Lösung, HEX="FF01" dann split bis FF(255) und 01(01)
InformationsquelleAutor Alejandro