整体思路
把量级(十/百/千/万/亿) 和 数字(一/二/三...)分别存入map中
遍历字符串,如果遇到数字,则对外层变量 num 赋值
如果遇到量级则将栈中数字弹出,弹出的数字和 num 相加,作为当前量级前面的数
处理完成后将数字重新入栈
最后将栈中所有数字弹出相加即可获取结果
代码
/**
* 补充题:中文数字转阿拉伯数字
* 中文转数字
*
* @author: dks
* @date: 2024/4/10 20:24
*/
public class CNToNumber {
// 量级
private static HashMap<Character, Long> level = new HashMap<>();
// 数字
private static HashMap<Character, Long> nums = new HashMap<>();
static {
// 小写
level.put('兆', 1000000000000L);
level.put('亿', 100000000L);
level.put('万', 10000L);
level.put('千', 1000L);
level.put('百', 100L);
level.put('十', 10L);
// 大写
level.put('萬', 10000L);
level.put('仟', 1000L);
level.put('佰', 100L);
level.put('拾', 10L);
// 小写
nums.put('零', 0L);
nums.put('一', 1L);
nums.put('二', 2L);
nums.put('三', 3L);
nums.put('四', 4L);
nums.put('五', 5L);
nums.put('六', 6L);
nums.put('七', 7L);
nums.put('八', 8L);
nums.put('九', 9L);
// 大写
nums.put('壹', 1L);
nums.put('贰', 2L);
nums.put('叁', 3L);
nums.put('肆', 4L);
nums.put('伍', 5L);
nums.put('陆', 6L);
nums.put('柒', 7L);
nums.put('捌', 8L);
nums.put('玖', 9L);
}
public long chNumToLong (String s) {
char[] cs = s.toCharArray();
int n = s.length();
// 用于装数字的栈
ArrayDeque<Long> stack = new ArrayDeque<>();
// 保存数字
long num = 0;
// 从左往右遍历
for (int i = 0; i < n; i++) {
// 如果是数字,直接赋值给当前数字
if (nums.containsKey(cs[i])) {
num = nums.get(cs[i]);
}
// 如果是量级,则将栈中小于当前量级的数字弹出,弹出的数字和num相加,作为当前量级前面的数
if (level.containsKey(cs[i]) || i == n - 1) {
Long rate = 1L;
if (level.containsKey(cs[i])) {
rate = level.get(cs[i]);
}
while (!stack.isEmpty() && rate > stack.peek()) {
num += stack.poll();
}
// 重新入栈
stack.push(num * rate);
// 重置数字
num = 0;
}
}
// 将栈中所有数字取出相加
long sum = 0;
for (Long l : stack) {
sum += l;
}
return sum;
}
@Test
public void Test () {
System.out.println(chNumToLong("三万叁仟零肆拾伍亿零贰佰萬柒仟陆佰零伍"));
}
}