黑马程序员——金额转换,阿拉伯数字转换成中文大写

package com.heima.problemA;

import java.util.ArrayList;
import java.util.List;

/* 
 * 思路: 待转换的整数分为两类:
 * 第一类是低于16位的数,把这个数从右至左分成4段,每段单独转换
 * 再分别用单位("万", "亿", "兆")拼接起来
 * 
 * 第二类是超过16位的数,它的低12位按常规方式转换(作为第一类数转换)
 * 剩下的位直接映射成中文大写,再用"兆"连接起来就OK
 * 
 * 编码时注意去掉多余的零
 *  
 */

/**
 * 将指定的整数转换为中文大写
 * 
 * @author fengyan 2011-12-29
 */
public class TransferAmount {

	/**
	 * 将指定的数转换为中文大写
	 * 
	 * @param amount
	 * @return
	 */
	public static String transferAmount(String amount) {
		if (amount == null || "".equals(amount))
			return null;

		// 处理大于16位的数
		if (amount.length() > 16) {
			String low12Bit = amount.substring(amount.length() - 12);
			String highBit = amount.substring(0, amount.length() - 12);

			low12Bit = transfer16Bit(low12Bit);
			highBit = processHightBit(highBit);

			return highBit + "兆" + low12Bit + "圆整";

		} else {// 处理小于16位的数
			return transfer16Bit(amount) + "圆整";
		}
	}

	/**
	 * 将超过16位的数中高于12位的数直接映射成中文大写
	 * 
	 * @param highBit
	 * @return
	 */
	private static String processHightBit(String highBit) {
		String[] nums = new String[] { "零", "壹", "貮", "叁", "肆", "伍", "陆", "柒",
				"捌", "玖" };
		StringBuffer sb = new StringBuffer();

		for (int i = 0; i < highBit.length(); i++) {
			sb.append(nums[highBit.charAt(i) - '0']);
		}

		return sb.toString();
	}

	/**
	 * 转换低于16位的数为中文大写
	 * 
	 * @param amount
	 * @return
	 */
	private static String transfer16Bit(String amount) {
		// 从右边开始每四位分割后的数
		List<String> segs = split(amount);
		String[] units = new String[] { "", "万", "亿", "兆" };

		StringBuffer result = new StringBuffer();

		for (int i = 0; i < segs.size(); i++) {
			String seg = segs.get(i);

			if (seg.length() != 0)
				result.insert(0, transferSegment(seg) + units[i]);
			if (seg.length() < 4)
				result.insert(0, "零");
		}

		return adjustment(result);
	}

	/**
	 * 调整:去前导零、后导零,连续的零改成一个零
	 * 
	 * @param sb
	 * @return
	 */
	private static String adjustment(StringBuffer sb) {
		String s = sb.toString();
		s = s.replaceAll("零+", "零");
		s = s.replaceAll("^零+", "");
		s = s.replaceAll("零+{1}quot;, "");
		return s;
	}

	/**
	 * 将分割后的4位数转为中文大写
	 * 
	 * @param segment
	 * @return
	 */
	private static String transferSegment(String segment) {

		String[] nums = new String[] { "零", "壹", "貮", "叁", "肆", "伍", "陆", "柒",
				"捌", "玖" };
		String[] units = new String[] { "", "拾", "佰", "仟" };

		StringBuffer sb = new StringBuffer();
		int len = segment.length();

		boolean zf = false; // 零标志

		for (int i = len - 1; i >= 0; i--) {
			// 处理0的情况
			if (segment.charAt(i) == '0') {
				if (zf) {
					sb.insert(0, "零");// 连续的0只插入一个"零"
					while (i > 0 && segment.charAt(--i) == '0')
						;
					i++;
				}
				continue;
			}

			int index = Integer.valueOf(segment.charAt(i)) - '0';
			String num = nums[index];

			int unitIndex = len - i - 1;
			String unit = units[unitIndex];

			sb.insert(0, num + unit);
			zf = true;
		}

		if (sb.length() == 0)
			sb.append("零");

		return sb.toString();
	}

	/**
	 * 将指定的数从右边开始每四位分割
	 * 
	 * @param src
	 * @return
	 */
	private static List<String> split(String src) {
		List<String> list = new ArrayList<String>();

		StringBuffer sb = new StringBuffer(src);
		sb = sb.reverse();

		StringBuffer seg = null;

		int start = 0, end = 4;
		for (; end < sb.length(); start += 4, end += 4) {
			seg = new StringBuffer(sb.subSequence(start, end)).reverse();

			// 去掉前导0
			int i = 0;
			while (i < seg.length() && seg.charAt(i) == '0') {
				seg.deleteCharAt(i);
			}

			list.add(seg.toString());
		}

		if (start < sb.length()) {
			end = sb.length();
			seg = new StringBuffer(sb.subSequence(start, end)).reverse();

			// 去掉前导0
			int i = 0;
			while (i < seg.length() && seg.charAt(i) == '0') {
				seg.deleteCharAt(i);
			}

			list.add(seg.toString());
		}

		return list;
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值