题目:
问题描述
从键盘输入一个不超过8位的正的十六进制数字符串,将它转换为正的十进制数后输出。
注:十六进制数中的10~15分别用大写的英文字母A、B、C、D、E、F表示。
样例输入
FFFF
样例输出
65535
题解
在Java中,各个整数类型byte、short、int、long,其中int占用的存储空间为4字节,也就是32bit。表示的范围是:-2^31到(2 ^31)-1。
然而,本道题中,输入的正16进制数的最大值为FFFF FFFF,即8字节,64bit,对应的值为:2^63。超出了int型数的表示 范围。
在解这道题的过程中,有两个实现方式:
(1)利用基本的转换思想,16进制转换为10进制数,所得到的10进制数为:16进制数每一位上的字面量 * 该位上所代表的的单位大小。例如:EF,转换为10进制数的计算过程为:15 * 16^0 + 15 * 16^1= 255
具体的实现如下:
解题思路为:
/*
- 解题思路:
- 从16进制数的最低位开始进行计算
- 设置sum(计算对应的10进制,类型为long),value(代表该位上的单位----对应着16的多少次方)
- 其中,对输入的16进制数,按照string进行存储,利用charAt(),读取每一位上的16进制的字符,
- 对16进制数进行遍历时,可以采用switch-case语句:(或者if-else语句)
- 如果值>‘A’,则转化为 n - ‘A’ +10
- 如果值<‘A’,则转化为 n - ‘0’
*/
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
String str = scan.nextLine();
long sum = 0L;//存储转化到10进制以后的值
long value = 1L;//代表该位上的16进制数,转化为10进制数时的权重
for(int i=str.length()-1;i>=0;i--) {
if(str.charAt(i)>='A') {
sum += (str.charAt(i)-'A'+10) * value;
value *= 16;
}else {
sum += (str.charAt(i) - '0') * value;
value *= 16;
}
}
System.out.print(sum);
}
}
(2)上述的转换思路,其实也是很简单的。只不过,后来发现在Java提供的API中,其实封装了解决进制转换问题的方法:
例如,对于本题,转换之后的数 定义为long型,才可以保证不会出现转换之后的数字 溢出的情况,所以选择 long型。
在包装类 Long,中,提供了用于数字转换的方法:
public static Long valueOf(String s,
int radix)
throws NumberFormatException
jdk 8 API中的valueOf(String s,int radix) 方法,
该方法的功能为:
本题调用该方法的具体实现代码为:
import java.util.Scanner;
public class MaxMain {
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
String line = scan.nextLine();
// 16转10进制
/*
* 利用的是long对应的包装类long中的方法,
* jdk 8 API中的valueOf(String s,int radix) 方法
* 最终的到的结果是,Long类型的value,
* 并在输出时利用自动拆箱,直接用value输出转化后的结果
*/
Long value = Long.valueOf(line, 16);
System.out.println(value);
//关闭输入流
scan.close();
}
}