mirror of
https://gitee.com/dromara/hutool.git
synced 2025-04-05 17:37:59 +08:00
commit
fc47566ddc
@ -0,0 +1,52 @@
|
||||
package cn.hutool.core.convert;
|
||||
|
||||
/**
|
||||
* @author totalo
|
||||
* @since 5.6.0
|
||||
* 中文转数字结构
|
||||
*/
|
||||
public final class ChineseNameValue {
|
||||
/**
|
||||
* 中文权名称
|
||||
*/
|
||||
String name;
|
||||
/**
|
||||
* 10的倍数值
|
||||
*/
|
||||
int value;
|
||||
|
||||
/**
|
||||
* 是否为节权位
|
||||
*/
|
||||
boolean secUnit;
|
||||
|
||||
public ChineseNameValue(String name, int value, boolean secUnit) {
|
||||
this.name = name;
|
||||
this.value = value;
|
||||
this.secUnit = secUnit;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public int getValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
public void setValue(int value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public boolean isSecUnit() {
|
||||
return secUnit;
|
||||
}
|
||||
|
||||
public void setSecUnit(boolean secUnit) {
|
||||
this.secUnit = secUnit;
|
||||
}
|
||||
}
|
@ -33,6 +33,18 @@ public class NumberChineseFormatter {
|
||||
**/
|
||||
private static final String[] TRADITIONAL_UNITS = {"", "拾", "佰", "仟"};
|
||||
|
||||
/**
|
||||
* 汉字转阿拉伯数字的
|
||||
*/
|
||||
private static final ChineseNameValue[] CHINESE_NAME_VALUE = {
|
||||
new ChineseNameValue("十", 10, false),
|
||||
new ChineseNameValue("百", 100, false),
|
||||
new ChineseNameValue("千", 1000, false),
|
||||
new ChineseNameValue("万", 10000, true),
|
||||
new ChineseNameValue("亿", 100000000, true),
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* 阿拉伯数字转换成中文,小数点后四舍五入保留两位. 使用于整数、小数的转换.
|
||||
*
|
||||
@ -193,4 +205,79 @@ public class NumberChineseFormatter {
|
||||
}
|
||||
return chineseStr.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* 把中文转换为数字 如 二百二 220
|
||||
* @see <url>https://www.d5.nz/read/sfdlq/text-part0000_split_030.html</url>
|
||||
* @param chinese 中文字符
|
||||
* @return
|
||||
*/
|
||||
public static int chineseToNumber(String chinese) {
|
||||
int pos = 0;
|
||||
int rtn = 0;
|
||||
int section = 0;
|
||||
int number = 0;
|
||||
boolean secUnit = false;
|
||||
while (pos < chinese.length()) {
|
||||
int num = chineseToValue(chinese.substring(pos, pos + 1));
|
||||
if (num >= 0) {
|
||||
number = num;
|
||||
pos += 1;
|
||||
if (pos >= chinese.length()) {
|
||||
section += number;
|
||||
rtn += section;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
int unit = 1;
|
||||
int tmp = chineseToUnit(chinese.substring(pos, pos + 1));
|
||||
if (tmp != -1) {
|
||||
unit = CHINESE_NAME_VALUE[tmp].getValue();
|
||||
secUnit = CHINESE_NAME_VALUE[tmp].isSecUnit();
|
||||
}
|
||||
if (secUnit) {
|
||||
section = (section + number) * unit;
|
||||
rtn += section;
|
||||
section = 0;
|
||||
} else {
|
||||
section += (number * unit);
|
||||
}
|
||||
number = 0;
|
||||
pos += 1;
|
||||
if (pos >= chinese.length()) {
|
||||
rtn += section;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return rtn;
|
||||
}
|
||||
|
||||
/**
|
||||
* 中文到数字的转换
|
||||
* @param chinese
|
||||
* @return
|
||||
*/
|
||||
private static int chineseToValue(String chinese) {
|
||||
for (int i = 0; i < SIMPLE_DIGITS.length; i++) {
|
||||
if (SIMPLE_DIGITS[i].equals(chinese)) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* 查找对应的权
|
||||
* @param chinese
|
||||
* @return
|
||||
*/
|
||||
private static int chineseToUnit(String chinese) {
|
||||
for (int i = 0; i < CHINESE_NAME_VALUE.length; i++) {
|
||||
if (CHINESE_NAME_VALUE[i].getName().equals(chinese)) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import org.junit.Assert;
|
||||
import org.junit.Test;
|
||||
|
||||
public class NumberChineseFormatterTest {
|
||||
|
||||
|
||||
@Test
|
||||
public void formatTest() {
|
||||
String f1 = NumberChineseFormatter.format(10889.72356, false);
|
||||
@ -24,7 +24,7 @@ public class NumberChineseFormatterTest {
|
||||
f1 = NumberChineseFormatter.format(0.05, false);
|
||||
Assert.assertEquals("零点零五", f1);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void formatTest2() {
|
||||
String f1 = NumberChineseFormatter.format(-0.3, false, false);
|
||||
@ -33,7 +33,7 @@ public class NumberChineseFormatterTest {
|
||||
f1 = NumberChineseFormatter.format(10, false, false);
|
||||
Assert.assertEquals("一十", f1);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void formatTraditionalTest() {
|
||||
String f1 = NumberChineseFormatter.format(10889.72356, true);
|
||||
@ -53,15 +53,15 @@ public class NumberChineseFormatterTest {
|
||||
f1 = NumberChineseFormatter.format(0.05, true);
|
||||
Assert.assertEquals("零点零伍", f1);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void digitToChineseTest() {
|
||||
String digitToChinese = Convert.digitToChinese(12412412412421.12);
|
||||
Assert.assertEquals("壹拾贰万肆仟壹佰贰拾肆亿壹仟贰佰肆拾壹万贰仟肆佰贰拾壹元壹角贰分", digitToChinese);
|
||||
|
||||
|
||||
String digitToChinese2 = Convert.digitToChinese(12412412412421D);
|
||||
Assert.assertEquals("壹拾贰万肆仟壹佰贰拾肆亿壹仟贰佰肆拾壹万贰仟肆佰贰拾壹元整", digitToChinese2);
|
||||
|
||||
|
||||
String digitToChinese3 = Convert.digitToChinese(2421.02);
|
||||
Assert.assertEquals("贰仟肆佰贰拾壹元零贰分", digitToChinese3);
|
||||
}
|
||||
@ -79,4 +79,19 @@ public class NumberChineseFormatterTest {
|
||||
s = NumberChineseFormatter.numberCharToChinese('A', false);
|
||||
Assert.assertEquals("A", s);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void chineseToNumberTest(){
|
||||
Assert.assertEquals(0, NumberChineseFormatter.chineseToNumber("零"));
|
||||
|
||||
Assert.assertEquals(102, NumberChineseFormatter.chineseToNumber("一百零二"));
|
||||
|
||||
Assert.assertEquals(112, NumberChineseFormatter.chineseToNumber("一百一十二"));
|
||||
|
||||
Assert.assertEquals(1012, NumberChineseFormatter.chineseToNumber("一千零一十二"));
|
||||
|
||||
Assert.assertEquals(1000000, NumberChineseFormatter.chineseToNumber("一百万"));
|
||||
|
||||
Assert.assertEquals(2000100112, NumberChineseFormatter.chineseToNumber("二十亿零一十万零一百一十二"));
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user