Convertir cadena hexadecimal en int

111

Estoy tratando de convertir una cadena que tiene 8 caracteres de código hexadecimal en un número entero para poder hacer una comparación int en lugar de comparaciones de cadenas sobre muchos valores diferentes.

Sé que esto es bastante trivial en C ++, pero necesito hacerlo en Java. El caso de prueba que necesito satisfacer es esencialmente Convertir "AA0F245C" a int y luego volver a esa cadena para saber que se está convirtiendo correctamente.

He probado lo siguiente:

int decode = Integer.decode("0xAA0F245C");  // NumberFormatException
int decode2 = Integer.decode("AA0F245C"); //NumberFormatException
int parseInt = Integer.parseInt("AA0F245C", 16); //NumberFormatException
int valueOf = Integer.valueOf("AA0F245C", 16); //NumberFormatException

También he intentado hacerlo dos caracteres a la vez y multiplicar los resultados, que funciona la conversión pero el número no es correcto.

int id = 0;
for (int h = 0; h < hex.length(); h= h+2)
{
    String sub = hex.subSequence(h, h+2).toString();

if (id == 0)
    id = Integer.valueOf(sub, 16);
else
    id *= Integer.valueOf(sub, 16);             
 }
//ID = 8445600 which = 80DEA0 if I convert it back. 

No puedo usar bibliotecas de terceros solo para que lo sepas, por lo que esto debe hacerse en las bibliotecas estándar de Java.

De forma anticipada, muchas gracias por su ayuda.

Roloc
fuente
Estás multiplicando cuando deberías cambiar.
Nathan Moinvaziri
7
0xAA0F245C = 2853119068peroInteger.MAX_VALUE = 0x7fffffff = 2147483647
Pshemo
5
Sé que la pregunta ha existido durante dos años. Sin embargo, java 8 habilita otra solución. Agregaron el Integer.parseUnsignedInt("value",radix)método que sirve a su propósito. Si el valor es mayor Integer.MAX_VALUE, se asigna a un número negativo.
Juan

Respuestas:

151

Es simplemente demasiado grande para un int (que tiene 4 bytes y está firmado).

Utilizar

Long.parseLong("AA0F245C", 16);
Denys Séguret
fuente
4
¡Increíble gracias! Probablemente debería haberlo sabido. Pero me hace sentir mejor, ninguna de las 4 personas a las que les pregunté antes de publicar lo sabía tampoco :) Como nota al margen, ahora tengo que averiguar por qué la persona escribió el código con el que necesito comparar los ints y los tiene como ints y no como long ... lo que probablemente significa que algo más está apagado. Eso es además del punto ... ¡¡¡Gracias por la rápida respuesta !!!! También te maldigo java por tu terrible mensaje de error ... "Es demasiado grande" hubiera sido útil.
Roloc
Cuando intento con una cadena hexadecimal grande, obtengo NumberFormatException: For input string: "AF0005E2A6C630059E4754B8799360F5"... ¿Solución?
Anum Sheraz
@AnumSheraz no desea convertir a una matriz larga sino a una matriz de bytes. Vea, por ejemplo, stackoverflow.com/questions/140131/…
Denys Séguret
Una alternativa a la conversión a una matriz de bytes para un gran número es usar la BigIntegerclase como esta:BigInteger value = new BigInteger(valueString, 16)
Javaru
33

puedes usar así

System.out.println(Integer.decode("0x4d2"))    // output 1234
//and vice versa 
System.out.println(Integer.toHexString(1234); //  output is 4d2);
manikant gautam
fuente
1
Me gusta esta respuesta, no sabía que hay un método genérico, insensible al tipo para esto en la clase Integer. gracias por el conocimiento.
Gewure
18

El valor máximo que Integerpuede manejar un Java es 2147483657 o 2 ^ 31-1. El número hexadecimal AA0F245C es 2853119068 como número decimal, y es demasiado grande, por lo que debe usar

Long.parseLong("AA0F245C", 16);

para que funcione.

Incompl
fuente
apagado: es interesante que una respuesta más detallada, aunque 5 minutos después, obtenga solo 1 voto a favor en comparación con 14. Aunque es cierto, este no dijo "4 bytes" mágicos y "firmado" ... hm.
n611x007
9

puede hacerlo fácilmente con parseInt con parámetro de formato.

Integer.parseInt("-FF", 16) ; // returns -255

javadoc entero

calor
fuente
el enlace está roto
odinthenerd
5

Esta es la respuesta correcta:

myPassedColor = "#ffff8c85" int colorInt = Color.parseColor(myPassedColor)

HannahCarney
fuente
3

Para aquellos de ustedes que necesitan convertir la representación hexadecimal de un byte con signo de una cadena de dos caracteres en un byte (que en Java siempre está firmado), hay un ejemplo. Analizar una cadena hexadecimal nunca da un número negativo, lo cual es defectuoso, porque 0xFF es -1 desde algún punto de vista (codificación de complemento a dos). El principio es analizar la cadena entrante como int, que es más grande que un byte, y luego envolver números negativos. Solo muestro bytes, por lo que ese ejemplo es lo suficientemente corto.

String inputTwoCharHex="FE"; //whatever your microcontroller data is

int i=Integer.parseInt(inputTwoCharHex,16);
//negative numbers is i now look like 128...255

// shortly i>=128
if (i>=Integer.parseInt("80",16)){

    //need to wrap-around negative numbers
    //we know that FF is 255 which is -1
    //and FE is 254 which is -2 and so on
    i=-1-Integer.parseInt("FF",16)+i;
    //shortly i=-256+i;
}
byte b=(byte)i;
//b is now surely between -128 and +127

Esto se puede editar para procesar números más largos. Simplemente agregue más FF o 00 respectivamente. Para analizar 8 enteros con signo de caracteres hexadecimales, debe utilizar Long.parseLong, porque FFFF-FFFF, que es un entero -1, no encajaría en Integer cuando se representa como un número positivo (da 4294967295). Entonces necesitas Long para almacenarlo. Después de la conversión a un número negativo y volver a convertirlo en Integer, encajará. No hay una cadena hexadecimal de 8 caracteres, que no se ajusta a un número entero al final.

JanSmrz
fuente
1

Una opción adicional a las sugeridas es utilizar la BigIntegerclase. Dado que los valores hexadecimales suelen ser números grandes, como los valores sha256 o sha512, se desbordarán fácilmente de un inty un long. Si bien la conversión a una matriz de bytes es una opción, como muestran otras respuestas BigInterger, la clase a menudo olvidada en java también es una opción.

String sha256 = "65f4b384672c2776116d8d6533c69d4b19d140ddec5c191ea4d2cfad7d025ca2";
BigInteger value = new BigInteger(sha256, 16);
System.out.println("value = " + value);
// 46115947372890196580627454674591875001875183744738980595815219240926424751266
Javaru
fuente
0
//Method for Smaller Number Range:
Integer.parseInt("abc",16);

//Method for Bigger Number Range.
Long.parseLong("abc",16);

//Method for Biggest Number Range.
new BigInteger("abc",16);
Nitish Kumar
fuente
0

Prueba con esto:

long abc = convertString2Hex ("1A2A3B");

private  long  convertString2Hex(String numberHexString)
{
    char[] ChaArray = numberHexString.toCharArray();
    long HexSum=0;
    long cChar =0;

    for(int i=0;i<numberHexString.length();i++ )
    {
        if( (ChaArray[i]>='0') && (ChaArray[i]<='9') )
            cChar = ChaArray[i] - '0';
        else
            cChar = ChaArray[i]-'A'+10;
        HexSum = 16 * HexSum + cChar;
    }
    return  HexSum;
}
Josko Marsic
fuente