汉字转数字(字节笔试题)

356 阅读1分钟

题目:

给定一个字符串 '一亿六千七百万零五十',将该字符串转为数字

例:将一亿六千七百万零五十转为167000050

思路:

  • '一亿六千七百万零五十' 可以分为 '一亿' + '六千七百万' + '零五十'

  • 难的点在于:六千七百万 怎么计算?

    • 我们可以拿出个位的数,例如 0~9,用变量 single 记录,用变量 product 则记录乘积位,如 十,百,千...
    • 对于 一亿 ,很容易直接 一乘以亿 得到 一亿
    • 对于 六千七百万,不能直接计算
  • 我们可以创建一个数组 maxProducts 来记录最大的乘积

    • 例如:'一亿六千七百万零五十'
    • 我们存进 maxProducts 的应该是 ['亿', '万', '十']
  • 这时候,我们遍历该字符串'一亿六千七百万零五十',如果此时 productmaxProducts 对应的值相同,则可以直接计算 single * product,反之,我们用 sliceResult 记录。例如对于 六千七百万,先计算 六千+七百 得到 六千七百,然后 此时指针遍历到 字符,与 maxProducts 一致,则将 六千七百一万 即得到答案

  • 注意 十亿 的特殊值

js实现

function NumToChinese(str) {
    let num = {
        '零': 0, '一': 1, '二': 2, '三': 3, '四': 4, '五': 5, '六': 6, '七': 7, '八': 8, '九': 9
    }
    let sum = {
        '十': 10, '百': 100, '千': 1000, '万': 10000, '亿': 100000000
    }
    let maxProducts = [] // [亿,万...]
    for(let i = 0; i < str.length; i++) {
        const product = sum[str[i]]
        if(product) {
            while(maxProducts.length) {
                let lastProduct = maxProducts.pop()
                if(lastProduct > product) {
                    maxProducts.push(lastProduct)
                    break
                }
            }
            maxProducts.push(product)
        }
    }
    let result = 0, sliceResult = 0, single = 1 // 结果
    let maxIndex = 0 // 最大乘积数组索引
    for(let i = 0; i < str.length; i++) {
        if(num[str[i]]) {
            single = num[str[i]]
            if(i === str.length - 1) return result + single
        } else {
            let product = sum[str[i]], maxProduct = maxProducts[maxIndex]
            if(product === maxProduct) {
                result += ((sliceResult ? sliceResult : single) * maxProduct)
                sliceResult = 0
                maxIndex++
            } else sliceResult += (single * product)
        }
    }
    return result
}