将字符串转换为整数十六进制值的“奇怪”行为

4
我注意到Java不允许我将像2000000000这样的大数字存储为整数类型,但如果我存储相应的十六进制值,即int largeHex = 0x77359400,那就没有问题了。
因此,我的程序需要增加到2 ^ 32,略高于42亿。我测试了十六进制键0xffffffff,它允许我以这种形式存储为整数类型。
我的问题是,我必须从程序中提取一个十六进制字符串。
例如:
sT = "ffffffff";

int hexSt = Integer.valueOf(sT, 16).intValue();

这仅适用于较小的整数值

我收到一个错误

Exception in thread "main" java.lang.NumberFormatException: For input string: "ffffffff"

我只需要将这个值存储在整型变量中,例如:

int largeHex = 0xffffffff

哪个可以正常工作?

我使用整数是因为我的程序需要生成许多值。


1
为什么int j = 2000000000无法工作?20亿在31位内是可以容纳的。 - David R Tribble
6个回答

7
String hex = "FFFFFFFF"; // or whatever... maximum 8 hex-digits
int i = (int) Long.parseLong(hex, 16);

将结果作为带符号整数返回...

3

看起来答案已经没有什么可以补充的了,但值得澄清的是:

  • 在解析时抛出异常,因为ffffffff对于整数来说太大了。考虑使用Integer.parseInt(""+Long.MAX_VALUE);,而不是使用十六进制表示法。这里也会抛出相同的异常。
  • int i = 0xffffffff;i设置为-1
  • 如果您已经决定使用长整型而不是整型,请注意long l = 0xffffffff;也会将l设置为-1,因为0xffffffff被视为一个整数。正确的形式是long l = 0xffffffffL;

没有问题吗?我是不是漏掉了什么?我声明0xffffffff作为一个整数没有问题,并且可以读取回来的值。 - user524156
抱歉,示例代码如下: int test = 0xffffffff System.out.println("test = "+Integer.toHexString(test)); - user524156
所以我的问题是,如果我可以将一个整数声明为该值,那么为什么如果我将其放在字符串中,就不能将整数分配给该值? - user524156
因为James Gosling想要这样做 :) 你可以写int i = (int)Long.MAX_VALUE;,它将是-1。我同意这很奇怪,因为编译器会抱怨int i = 4294967295;但不会抱怨int i = 0xffffffff;。我认为,基本上这是因为0x...被视为一个位序列,然后被转换为所需的类型。 - khachik
我被卡住了,听起来我需要做的很简单,但是我必须有一个方法。 - user524156
哈哈,谢谢你的回答。我浪费了一整天的时间来尝试让整数工作。另外一个我发现的问题是,虽然Java允许你将一个43亿的十六进制数赋值给一个int类型,并且打印这个值也没问题,但是当涉及到比较或任何算术运算时,它就不起作用了,这非常具有误导性。 - user524156

2

使用以下代码如何:


System.out.println(Long.valueOf("ffffffff", 16).longValue());

这将输出:

4294967295
该代码可以将十六进制字符串转换为长整型并输出其值。

我需要将一个十六进制字符串转换为一个整数十六进制,而不是将其打印出来。正如我所说,我可以将一个int赋值为0xffffffff并使用它进行递增、读取等操作。但是,如果我有一个字符串"ffffffff",我该如何将其分配给一个十六进制int,以前的方式,而不会出现重大错误? - user524156
为了能够处理这样一个大的值,您必须使用“long”Java原始类型而不是“int”,即:<code>long value = Long.valueOf("ffffffff", 16).longValue();</code> - Jiri Patera

2
< p >整型数据类型int是有符号的,可以存储高达2^31的值,只能存储您所需一半的值。但是,您可以使用长整型long,它具有64位长度,可以存储高达2^63的值。< /p> < p >希望这将解决您在16进制值方面的所有问题 =)< /p>

没有问题,我已经成功将整数值存储为16进制格式,最大可达2^32-1。 - user524156
只要将变量声明为long,就不需要使用十六进制。在您的代码中,将“int”替换为“long”即可。 - gsteinert
是的,我现在正在使用longs。事实是Java允许对整数进行签名,最高可达43亿,只要它以十六进制表示,我认为很好,我会使用int来节省磁盘空间,当写出这些数十亿个键时,但最终行为变得太奇怪了,所以我转而使用long。 - user524156
我认为数据类型的命名是造成混淆的原因。int和long都是整型数据类型(与byte和short一起),但它们是不同大小的整型类型。如果您查看C++如何定义它们,可能会更容易理解 - 在Java中,long被定义为C++中的long int,就像您还可以使用 short intunsigned int一样。所有整数类型,但允许存储不同范围的值。 - gsteinert

0

int test = 0xFFFFFF; int test2 = Integer.parseInt(Integer.toHexString(test), 16);

^---这个可以正常工作...但是:

int test = 0xFFFFFFFF; int test2 = Integer.parseInt(Integer.toHexString(test), 16);

^--这个会抛出一个数字格式异常。

int test = 0xFFFFFFFF; int test2 = (int)Long.parseLong(Integer.toHexString(test), 16);

^--这个可以正常工作。


0

我无法像所述的那样生成2^32个密钥,我必须将它们写入文件中,也不能使用大整数。 - user524156
你可以将 <code>BigInteger</code> 实例以 <code>String</code> 的形式写入文件。<pre><code> BigInteger bi = new BigInteger("ffffffff", 16); String s = bi.toString(); Writer w = null; try { w = new BufferedWriter(new FileWriter("filename.txt")); w.write(s); } finally { if (w != null) { w.close(); } } </code></pre> - Jiri Patera

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接