Integer.parseInt转十六进制必须显式指定基数16,否则按十进制解析;字符串须为纯0-9a-fA-F字符,不支持0x前缀、空格、负号等;超范围用Long.parseLong或BigInteger更安全。

Java里用Integer.parseInt转十六进制字符串,必须传16
不指定基数或传错值(比如10),会直接抛NumberFormatException。Java默认按十进制解析,哪怕字符串是"FF"这种明显是十六进制的写法,它也认不出来。
实操建议:
-
Integer.parseInt("FF", 16)→ 正确,返回255 -
Integer.parseInt("FF")→ 错误,抛异常 -
Integer.parseInt("0xFF", 16)→ 错误,前缀0x不是合法十六进制数字字符,会被当作非法字符截断或报错 - 字符串含空格、换行、不可见控制符?先
.trim(),否则同样触发NumberFormatException
遇到NumberFormatException,先检查输入合法性
这个异常不是“方法用错了”,而是输入不符合parseInt对“纯数字字符串”的硬性要求。十六进制允许的字符只有0-9和a-f/A-F,多一个-、0x、空格、中文全角字符都会崩。
常见错误现象:
立即学习“Java免费学习笔记(深入)”;
-
Integer.parseInt("0x1A", 16)→ 报错,因为'0'和'x'不在十六进制字符集里 -
Integer.parseInt("1a ", 16)→ 报错,末尾空格不被忽略 -
Integer.parseInt("1G", 16)→ 报错,G超出十六进制范围
使用场景提示:如果数据来源不可控(比如HTTP参数、文件读取),别急着parse,先用正则^[0-9a-fA-F]+$粗筛,或用String.replaceAll("[^0-9a-fA-F]", "")清洗——但注意这会静默丢数据,得看业务是否允许。
大写小写、前缀、负数这些细节怎么处理
Integer.parseInt本身不区分大小写,"ff"、"FF"、"Ff"都行;但它不支持任何前缀,也不支持负号开头的十六进制表示(比如"-FF"不是标准写法,应转成补码再解析,或先去掉负号再手动加负)。
参数差异与兼容性影响:
- 用
Integer.decode("0xFF")可以自动识别0x前缀,但它内部仍调用parseInt,且不支持0X(大写X)或#FF等变体 - 如果数值可能超
int范围(比如"FFFFFFFF"),要用Long.parseLong(str, 16),否则溢出后结果错误但不报错 - Android API 26+ 支持
Integer.parseUnsignedInt(str, 16),能安全解析"FFFFFFFF"为4294967295,老版本只能自己处理
为什么不用new BigInteger(str, 16)
当输入长度不确定、可能极大(比如哈希值、密钥片段),或者你根本不确定它是不是在int/long范围内时,BigInteger最省心。它不抛溢出异常,构造失败才抛NumberFormatException,而且天然支持0x前缀(只要去掉空格)。
但代价是对象开销大,频繁调用会影响性能。所以日常ID、状态码、配置值这类已知长度≤8位的,坚持用parseInt更轻量。
容易被忽略的地方:十六进制字符串如果是从二进制数据转出来的(比如bytesToHex),要确认它没带分隔符(如"FF-FF-FF")、没混入调试日志(如"hex: FF")。这种脏数据不会报错,但结果完全不对——问题不在解析逻辑,而在上游清洗漏了。


















