今天做了一个题,需要把数字转为汉字,想了一段时间没有结果,于是在网上搜索出了如下方法:
1 package com.b510.number2char; 2 3 import java.math.BigDecimal; 4 5 /** 6 * 数字转换为汉语中人民币的大写<br> 7 * 8 * @author hongten 9 * @contact [email protected] 10 * @create 2013-08-13 11 */ 12 public class NumberToCN { 13 /** 14 * 汉语中数字大写 15 */ 16 private static final String[] CN_UPPER_NUMBER = { "零", "壹", "贰", "叁", "肆", 17 "伍", "陆", "柒", "捌", "玖" }; 18 /** 19 * 汉语中货币单位大写,这样的设计类似于占位符 20 */ 21 private static final String[] CN_UPPER_MONETRAY_UNIT = { "分", "角", "元", 22 "拾", "佰", "仟", "万", "拾", "佰", "仟", "亿", "拾", "佰", "仟", "兆", "拾", 23 "佰", "仟" }; 24 /** 25 * 特殊字符:整 26 */ 27 private static final String CN_FULL = "整"; 28 /** 29 * 特殊字符:负 30 */ 31 private static final String CN_NEGATIVE = "负"; 32 /** 33 * 金额的精度,默认值为2 34 */ 35 private static final int MONEY_PRECISION = 2; 36 /** 37 * 特殊字符:零元整 38 */ 39 private static final String CN_ZEOR_FULL = "零元" + CN_FULL; 40 41 /** 42 * 把输入的金额转换为汉语中人民币的大写 43 * 44 * @param numberOfMoney 45 * 输入的金额 46 * @return 对应的汉语大写 47 */ 48 public static String number2CNMontrayUnit(BigDecimal numberOfMoney) { 49 StringBuffer sb = new StringBuffer(); 50 // -1, 0, or 1 as the value of this BigDecimal is negative, zero, or 51 // positive. 52 int signum = numberOfMoney.signum(); 53 // 零元整的情况 54 if (signum == 0) { 55 return CN_ZEOR_FULL; 56 } 57 //这里会进行金额的四舍五入 58 long number = numberOfMoney.movePointRight(MONEY_PRECISION) 59 .setScale(0, 4).abs().longValue(); 60 // 得到小数点后两位值 61 long scale = number % 100; 62 int numUnit = 0; 63 int numIndex = 0; 64 boolean getZero = false; 65 // 判断最后两位数,一共有四中情况:00 = 0, 01 = 1, 10, 11 66 if (!(scale > 0)) { 67 numIndex = 2; 68 number = number / 100; 69 getZero = true; 70 } 71 if ((scale > 0) && (!(scale % 10 > 0))) { 72 numIndex = 1; 73 number = number / 10; 74 getZero = true; 75 } 76 int zeroSize = 0; 77 while (true) { 78 if (number <= 0) { 79 break; 80 } 81 // 每次获取到最后一个数 82 numUnit = (int) (number % 10); 83 if (numUnit > 0) { 84 if ((numIndex == 9) && (zeroSize >= 3)) { 85 sb.insert(0, CN_UPPER_MONETRAY_UNIT[6]); 86 } 87 if ((numIndex == 13) && (zeroSize >= 3)) { 88 sb.insert(0, CN_UPPER_MONETRAY_UNIT[10]); 89 } 90 sb.insert(0, CN_UPPER_MONETRAY_UNIT[numIndex]); 91 sb.insert(0, CN_UPPER_NUMBER[numUnit]); 92 getZero = false; 93 zeroSize = 0; 94 } else { 95 ++zeroSize; 96 if (!(getZero)) { 97 sb.insert(0, CN_UPPER_NUMBER[numUnit]); 98 } 99 if (numIndex == 2) { 100 if (number > 0) { 101 sb.insert(0, CN_UPPER_MONETRAY_UNIT[numIndex]); 102 } 103 } else if (((numIndex - 2) % 4 == 0) && (number % 1000 > 0)) { 104 sb.insert(0, CN_UPPER_MONETRAY_UNIT[numIndex]); 105 } 106 getZero = true; 107 } 108 // 让number每次都去掉最后一个数 109 number = number / 10; 110 ++numIndex; 111 } 112 // 如果signum == -1,则说明输入的数字为负数,就在最前面追加特殊字符:负 113 if (signum == -1) { 114 sb.insert(0, CN_NEGATIVE); 115 } 116 // 输入的数字小数点后两位为"00"的情况,则要在最后追加特殊字符:整 117 if (!(scale > 0)) { 118 sb.append(CN_FULL); 119 } 120 return sb.toString(); 121 } 122 123 public static void main(String[] args) { 124 double money = 2020004.01; 125 BigDecimal numberOfMoney = new BigDecimal(money); 126 String s = NumberToCN.number2CNMontrayUnit(numberOfMoney); 127 System.out.println("你输入的金额为:【"+ money +"】 #--# [" +s.toString()+"]"); 128 } 129 }
非常感谢:http://www.cnblogs.com/hongten/p/hongten_java_money.html提供的参考
如下是按照自己的理解写的类似方法:
1 package com.numbertoch; 2 3 import java.math.BigDecimal; 4 5 /** 6 * @author simon - zhou 7 * @version v1.0 8 */ 9 public class NumberToBigCh 10 { 11 /** 12 * 汉语中数字大写 13 */ 14 private static final String[] CN_UPPER_NUMBER = { "零", "壹", "贰", "叁", "肆", 15 "伍", "陆", "柒", "捌", "玖" }; 16 /** 17 * 汉语中货币单位大写,这样的设计类似于占位符 18 */ 19 private static final String[] CN_UPPER_MONETRAY_UNIT = { "分", "角", "元", 20 "拾", "佰", "仟", "万", "拾", "佰", "仟", "亿", "拾", "佰", "仟", "兆", "拾", 21 "佰", "仟" }; 22 /** 23 * 特殊字符:整 24 */ 25 private static final String CN_FULL = "整"; 26 /** 27 * 特殊字符:负 28 */ 29 private static final String CN_NEGATIVE = "负"; 30 /** 31 * 金额的精度,默认值为2 32 */ 33 private static final int MONEY_PRECISION = 2; 34 /** 35 * 特殊字符:零元整 36 */ 37 private static final String CN_ZEOR_FULL = "零元" + CN_FULL; 38 39 /** 40 * 把输入的金额转换为汉语中人民币的大写 41 * 42 * @param numberOfMoney 43 * 输入的金额 44 * @return 对应的汉语大写 45 */ 46 public static String number2CNMontrayUnit1(BigDecimal numberOfMoney) 47 { 48 StringBuffer sb = new StringBuffer(); 49 // 判断这个数字是整数 负数 或者 0 : 1 -1 0 50 int signum = numberOfMoney.signum(); 51 // 零元整的情况 52 if (signum == 0) 53 { 54 return CN_ZEOR_FULL; 55 } 56 // 向右移动2位后,按照四舍五入的精度保留0位,并转为long类型 57 // 这样移动位置,似乎有bug存在 58 long number = numberOfMoney.movePointRight(MONEY_PRECISION) 59 .setScale(0, 4).abs().longValue(); 60 // 得到小数点后两位值 61 long scale = number % 100; 62 System.out.println(240 % 100); 63 System.out.println(scale); 64 // 以下处理的是不包含小数的内容 65 number = number / 100; 66 String str = "" + number; 67 System.out.println(str); 68 long nowNum = 0; 69 boolean haveZero = false; 70 // 20200004.01 71 for (int i = 0; i < str.length(); i++) 72 { 73 nowNum = number % 10; 74 // 如果这个当前位的数字大于0,则添加数字和单位 75 if (nowNum > 0) 76 { 77 sb.insert(0, CN_UPPER_MONETRAY_UNIT[i + 2]); 78 sb.insert(0, CN_UPPER_NUMBER[(int) nowNum]); 79 // 本次不是零,则打开零的开关,允许下一次添零 80 haveZero = false; 81 } 82 else 83 { 84 sb.insert(0, CN_UPPER_NUMBER[0]); 85 // 添加零,但是不添加单位 - 如果前面已经添加过零,则不添加 86 if (haveZero) 87 { 88 sb = new StringBuffer(sb.substring(1)); 89 } 90 // 记录本次是零 - 放在else的最后 91 haveZero = true; 92 // 如果是元,万,亿,兆,则可以添加零 93 if (i % 4 == 0) 94 { 95 // 由于是元,万,亿,兆,所以去掉前面的零,并添加单位 96 sb.insert(0, CN_UPPER_MONETRAY_UNIT[i + 2]); 97 // 由于下四位和上四位单位不一致,所以上四位可以添加零 98 haveZero = false; 99 } 100 //System.out.println(sb.toString()); 101 } 102 number = number / 10; 103 } 104 String lastNum = sb.toString(); 105 String lastChar = lastNum.substring(lastNum.length() - 1); 106 //System.out.println(lastChar); 107 if (lastChar.equals(CN_UPPER_NUMBER[0])) 108 { 109 sb = new StringBuffer(sb.substring(0, lastNum.length() - 1)); 110 } 111 //System.out.println(sb.toString()); 112 // 替换特殊的情况 113 sb = new StringBuffer(sb.toString().replaceAll("零元", "")); 114 sb = new StringBuffer(sb.toString().replaceAll("零万", "")); 115 sb = new StringBuffer(sb.toString().replaceAll("零亿", "")); 116 sb = new StringBuffer(sb.toString().replaceAll("零兆", "")); 117 // 如果signum == -1,则说明输入的数字为负数,就在最前面追加特殊字符:负 118 if (signum == -1) 119 { 120 sb.insert(0, CN_NEGATIVE); 121 } 122 StringBuffer sb2 = new StringBuffer(); 123 // 处理小数位 124 // 输入的数字小数点后两位为"00"的情况,则要在最后追加特殊字符:整 125 if (!(scale > 0)) { 126 sb2.append(CN_FULL); 127 } 128 // 129 if (scale % 10 > 0) 130 { 131 sb2.insert(0, CN_UPPER_MONETRAY_UNIT[0]); 132 sb2.insert(0, CN_UPPER_NUMBER[(int) (scale % 10)]); 133 } 134 if (scale / 10 > 0) 135 { 136 sb2.insert(0, CN_UPPER_MONETRAY_UNIT[1]); 137 sb2.insert(0, CN_UPPER_NUMBER[(int) (scale / 10)]); 138 } 139 if (scale / 10 == 0 && scale % 10 > 0) 140 { 141 sb2.insert(0, CN_UPPER_NUMBER[0]); 142 } 143 sb.append(sb2.toString()); 144 return sb.toString(); 145 } 146 147 public static void main(String[] args) 148 { 149 // 约束条件:小数点后至少2位 150 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(6202000000202.0199))); 151 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(6202000000202.2199))); 152 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(6202000000200.4099))); 153 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(36202004500202.0199))); 154 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(26000000000202.0199))); 155 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(26000000000202.00))); 156 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(26000000000202.401))); 157 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(26000000000202.001))); 158 System.out.println(NumberToBigCh.number2CNMontrayUnit1(new BigDecimal(26000000000202.011))); 159 } 160 }
附上测试的运行结果:
由于本人思维不是很强,又不喜欢用while循环,平时通常就用用for循环,用用if之类的,就连else if都看着不舒服。所以代码很拙劣,请谅解。
时间: 2024-10-05 06:15:22