C# 如何将整数转换为其口头表示?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/554314/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-04 07:58:30  来源:igfitidea点击:

How can I convert an integer into its verbal representation?

c#.net.net-3.5

提问by Malfist

Is there a library or a class/function that I can use to convert an integer to it's verbal representation?

是否有库或类/函数可用于将整数转换为其口头表示?

Example input:

示例输入:

4,567,788`

4,567,788`

Example output:

示例输出:

Four million, Five hundred sixty-seven thousand, seven hundred eighty-eight

四百万、五十六万七千、七八十八

采纳答案by Ruben Carreon

if you use the code found in: converting numbers in to words C#and you need it for decimal numbers, here is how to do it:

如果您使用以下代码: 将数字转换为单词 C#并且您需要将其用于十进制数字,请按以下步骤操作:

public string DecimalToWords(decimal number)
{
    if (number == 0)
        return "zero";

    if (number < 0)
        return "minus " + DecimalToWords(Math.Abs(number));

    string words = "";

    int intPortion = (int)number;
    decimal fraction = (number - intPortion)*100;
    int decPortion = (int)fraction;

    words = NumericToWords(intPortion);
    if (decPortion > 0)
    {
        words += " and ";
        words += NumericToWords(decPortion);
    }
    return words;
}

回答by Joe Meyer

http://www.exchangecore.com/blog/convert-number-words-c-sharp-console-application/has some C# script that looks to handle very large numbers and very small decimals.

http://www.exchangecore.com/blog/convert-number-words-c-sharp-console-application/有一些 C# 脚本,可以处理非常大的数字和非常小的小数。

using System;
using System.Collections.Generic;
using System.Text;

namespace NumWords
{
    class Program
    {
        // PROGRAM HANDLES NEGATIVE AND POSITIVE DOUBLES


        static String NumWordsWrapper(double n)
        {
            string words = "";
            double intPart;
            double decPart = 0;
            if (n == 0)
                return "zero";
            try {
                string[] splitter = n.ToString().Split('.');
                intPart = double.Parse(splitter[0]);
                decPart = double.Parse(splitter[1]);
            } catch {
                intPart = n;
            }

            words = NumWords(intPart);

            if (decPart > 0) {
                if (words != "")
                    words += " and ";
                int counter = decPart.ToString().Length;
                switch (counter) {
                    case 1: words += NumWords(decPart) + " tenths"; break;
                    case 2: words += NumWords(decPart) + " hundredths"; break;
                    case 3: words += NumWords(decPart) + " thousandths"; break;
                    case 4: words += NumWords(decPart) + " ten-thousandths"; break;
                    case 5: words += NumWords(decPart) + " hundred-thousandths"; break;
                    case 6: words += NumWords(decPart) + " millionths"; break;
                    case 7: words += NumWords(decPart) + " ten-millionths"; break;
                }
            }
            return words;
        }

        static String NumWords(double n) //converts double to words
        {
            string[] numbersArr = new string[] { "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen" };
            string[] tensArr = new string[] { "twenty", "thirty", "fourty", "fifty", "sixty", "seventy", "eighty", "ninty" };
            string[] suffixesArr = new string[] { "thousand", "million", "billion", "trillion", "quadrillion", "quintillion", "sextillion", "septillion", "octillion", "nonillion", "decillion", "undecillion", "duodecillion", "tredecillion", "Quattuordecillion", "Quindecillion", "Sexdecillion", "Septdecillion", "Octodecillion", "Novemdecillion", "Vigintillion" };
            string words = "";

            bool tens = false;

            if (n < 0) {
                words += "negative ";
                n *= -1;
            }

            int power = (suffixesArr.Length + 1) * 3;

            while (power > 3) {
                double pow = Math.Pow(10, power);
                if (n >= pow) {
                    if (n % pow > 0) {
                        words += NumWords(Math.Floor(n / pow)) + " " + suffixesArr[(power / 3) - 1] + ", ";
                    } else if (n % pow == 0) {
                        words += NumWords(Math.Floor(n / pow)) + " " + suffixesArr[(power / 3) - 1];
                    }
                    n %= pow;
                }
                power -= 3;
            }
            if (n >= 1000) {
                if (n % 1000 > 0) words += NumWords(Math.Floor(n / 1000)) + " thousand, ";
                else words += NumWords(Math.Floor(n / 1000)) + " thousand";
                n %= 1000;
            }
            if (0 <= n && n <= 999) {
                if ((int)n / 100 > 0) {
                    words += NumWords(Math.Floor(n / 100)) + " hundred";
                    n %= 100;
                }
                if ((int)n / 10 > 1) {
                    if (words != "")
                        words += " ";
                    words += tensArr[(int)n / 10 - 2];
                    tens = true;
                    n %= 10;
                }

                if (n < 20 && n > 0) {
                    if (words != "" && tens == false)
                        words += " ";
                    words += (tens ? "-" + numbersArr[(int)n - 1] : numbersArr[(int)n - 1]);
                    n -= Math.Floor(n);
                }
            }

            return words;

        }
        static void Main(string[] args)
        {
            Console.Write("Enter a number to convert to words: ");
            Double n = Double.Parse(Console.ReadLine());

            Console.WriteLine("{0}", NumWordsWrapper(n));
        }
    }
}

EDIT: brought code over from blog post

编辑:从博客文章中带来了代码

回答by Mitch

Imports System.Text

Public Class NumberWriter

    Public Shared Function Parse(ByVal Number As String) As String
        If Not AreNumbers(Number) Then Return ""
        Dim TempQueue As New Queue(Of String)
        For Each ItemA As Char In Number.Replace(",", "").Reverse
            TempQueue.Enqueue(ItemA)
        Next
        Dim Blocks As New List(Of String)
        Dim BlockEmpty As New List(Of Boolean)
        Do
            Dim TempBlock As New StringBuilder(3)
            TempBlock.Append(TempQueue.Dequeue)
            If TempQueue.Count > 0 Then
                TempBlock.Append(TempQueue.Dequeue)
                If TempQueue.Count > 0 Then
                    TempBlock.Append(TempQueue.Dequeue)
                End If
            End If
            Blocks.Add(StrReverse(TempBlock.ToString))
            BlockEmpty.Add(TempBlock.ToString = "000")
            If TempQueue.Count < 1 Then Exit Do
        Loop
        Dim ResultStack As New Stack(Of String)
        For int1 As Integer = 0 To Blocks.Count - 1
            ResultStack.Push(ReadBlock(Blocks(int1)) & If(Not int1 = 0, If(Not BlockEmpty(int1), " " & CapitalizeWord(GetPlaceValueSet(int1)) & If(BlockEmpty(int1 - 1), "", ", "), ""), ""))
        Next
        Dim Result1 As String = ""
        Do Until ResultStack.Count < 1
            Result1 &= ResultStack.Pop
        Loop
        Return RemoveGrammarErrors(Result1)
    End Function

    Private Shared Function RemoveGrammarErrors(ByVal Str As String) As String
        Dim tstr As String = Str
        tstr.Replace("  ", " ")
        tstr.Replace(" , ", ", ")
        Return tstr
    End Function

    Private Shared Function AreNumbers(ByVal Str1 As String) As Boolean
        Dim Numbers() As String = {"0", "1", "2", "3", "4", "5", "6", "7", "8", "9", ","}
        For Each ItemA As Char In Str1
            Dim IsN As Boolean = False
            For Each ItemB As String In Numbers
                If ItemA = ItemB Then IsN = True
            Next
            If Not IsN Then
                Return False
            End If
        Next
        Return True
    End Function

    Private Shared Function ReadBlock(ByVal Block As String)
        Select Case Block.Length
            Case 1
                Return ReadSingleDigit(Block)
            Case 2
                Return ReadTwoDigits(Block)
            Case 3
                Return ReadThreeDigits(Block)
            Case Else
                Throw New Exception
        End Select
    End Function

    Private Shared Function ReadThreeDigits(ByVal Digits As String)
        If Digits.Length > 3 Then Throw New ArgumentException("There are too many digits.")
        Dim Result As String = ""
        If Not Digits(0) = "0" Then
            Result &= ReadSingleDigit(Digits(0)) & " Hundred "
        End If
        Result &= ReadTwoDigits(Digits.Substring(1))
        Return Result
    End Function

    Private Shared Function ReadTwoDigits(ByVal Digits As String)
        If Digits.Length > 2 Then Throw New ArgumentException("There are too many digits.")
        Select Case Digits(0)
            Case "0"
                Return ReadSingleDigit(Digits(1))
            Case "1"
                Return ReadTeenNumber(Digits)
            Case Else
                Return ReadFirstInNumberPair(Digits(0)) & If(Digits(1) = "0", "", "-" & ReadSingleDigit(Digits(1)))
        End Select
    End Function

    Private Shared Function ReadSingleDigit(ByVal Digit As String) As String
        If Not Digit.Length = 1 Then Throw New ArgumentException("There must be only one digit and it must be more than zero.")
        Select Case Digit
            Case "0"
                Return ""
            Case "1"
                Return "One"
            Case "2"
                Return "Two"
            Case "3"
                Return "Three"
            Case "4"
                Return "Four"
            Case "5"
                Return "Five"
            Case "6"
                Return "Six"
            Case "7"
                Return "Seven"
            Case "8"
                Return "Eight"
            Case "9"
                Return "Nine"
            Case Else
                Throw New Exception()
        End Select
    End Function

    Private Shared Function ReadTeenNumber(ByVal Num As String) As String
        Select Case Num
            Case "11"
                Return "Eleven"
            Case "12"
                Return "Twelve"
            Case "13"
                Return "Thirteen"
            Case "14"
                Return "Fourteen"
            Case "15"
                Return "Fifteen"
            Case "16"
                Return "Sixteen"
            Case "17"
                Return "Seventeen"
            Case "18"
                Return "Eighteen"
            Case "19"
                Return "Nineteen"
            Case Else
                Throw New Exception()
        End Select
    End Function

    Private Shared Function ReadFirstInNumberPair(ByVal Num As String) As String
        If Not (Num > 1 OrElse Num < 10) Then Throw New ArgumentException("Number must be more than 1 and less than 10")
        Select Case Num
            Case "2"
                Return "Twenty"
            Case "3"
                Return "Thirty"
            Case "4"
                Return "Fourty"
            Case "5"
                Return "Fifty"
            Case "6"
                Return "Sixty"
            Case "7"
                Return "Seventy"
            Case "8"
                Return "Eighty"
            Case "9"
                Return "Ninety"
            Case Else
                Throw New Exception()
        End Select
    End Function

    Private Shared Function CapitalizeWord(ByVal Word As String) As String
        Return Word.Substring(0, 1).ToUpper & Word.Substring(1)
    End Function

    Private Shared Function GetPlaceValueSet(ByVal Num As Byte) As String
        Select Case Num
            Case 0
                Return "" 'Hundreds
            Case 1
                Return "Thousand"
            Case 2
                Return "Million"
            Case 3
                Return "Billion"
            Case 4
                Return "Trillion"
            Case 5
                Return "Quadrillion"
            Case 6
                Return "Quintillion"
            Case 7
                Return "Sextillion"
            Case 8
                Return "Septillion"
            Case 9
                Return "Octillion"
            Case 10
                Return "Nonillion"
            Case 11
                Return "octillion"
            Case 12
                Return "nonillion"
            Case 13
                Return "decillion"
            Case 14
                Return "undecillion"
            Case 15
                Return "dodecillion,"
            Case 16
                Return "tredecillion"
            Case 17
                Return "quattuordecillion"
            Case 18
                Return "quindecillion"
            Case 19
                Return "sexdecillion"
            Case 20
                Return "septendecillion"
            Case 21
                Return "octodecillion"
            Case 22
                Return "novemdecillion"
            Case 23
                Return "vigintillion"
            Case 24
                Return "unvigintillion"
            Case 25
                Return "dovigintillion"
            Case 26
                Return "trevigintillion"
            Case 27
                Return "quattuorvigintillion"
            Case 28
                Return "quinvigintillion"
            Case 29
                Return "sexvigintillion"
            Case 30
                Return "septenvigintillion"
            Case 31
                Return "octovigintillion"
            Case 32
                Return "novemvigintillion"
            Case 33
                Return "trigintillion"
            Case 34
                Return "untrigintillion"
            Case 35
                Return "dotrigintillion"
            Case 36
                Return "tretrigintillion"
            Case 37
                Return "quattuortrigintillion"
            Case 38
                Return "quintrigintillion"
            Case 39
                Return "sextrigintillion"
            Case 40
                Return "septentrigintillion"
            Case 41
                Return "octotrigintillion"
            Case Else
                Throw New Exception
        End Select
    End Function
End Class

Sorry it's in VB.NET, but it works completely. It is one way. Number to Verbal. Handles numbers up to 123 characters long I believe.

对不起,它在 VB.NET 中,但它完全有效。这是一种方式。数字到口头。我相信最多可以处理 123 个字符的数字。

回答by Ahmar Husain

Here is my solution hope it will help you

这是我的解决方案希望它会帮助你

namespace ConsoleApplication3
{

    class Program
    {


        static void Main(string[] args)
        {

            string s = Console.ReadLine();
            ConvertMyword(int.Parse(s));

            Console.Read();

        }

        static void ConvertMyword(int number)
        {
            int flag = 0;
            int lflag = 0;
            string words = String.Empty;
            string[] places = { "ones", "ten", "hundred", "thousand", "ten thousand", "lacs","tenlacs","crore","tencrore" };
            string rawnumber = number.ToString();
            char[] a = rawnumber.ToCharArray();
            Array.Reverse(a);
            for (int i = a.Length - 1; i >= 0; i--)
            {
                if (i % 2 == 0 && i > 2)
                {
                    if (int.Parse(a[i].ToString()) > 1)
                    {
                        if (int.Parse(a[i - 1].ToString()) == 0)
                        {
                            words = words + getNumberStringty(int.Parse(a[i].ToString())) + " " + places[i - 1] + " ";
                        }
                        else
                        {
                            words = words + getNumberStringty(int.Parse(a[i].ToString())) + " ";
                        }
                    }
                    else if (int.Parse(a[i].ToString()) == 1)
                    {
                        if (int.Parse(a[i - 1].ToString())== 0)
                        {
                            words = words +"Ten" + " ";
                        }
                        else
                        {
                            words = words + getNumberStringteen(int.Parse(a[i - 1].ToString())) + " ";
                        }
                        flag = 1;
                    }
                }
                else
                {
                    if (i == 1 || i == 0)
                    {
                        if (int.Parse(a[i].ToString()) > 1)
                        {
                            words = words + getNumberStringty(int.Parse(a[i].ToString())) + " " + getNumberString(int.Parse(a[0].ToString())) + " ";
                            break;
                        }
                        else if (int.Parse(a[i].ToString()) == 1)
                        {
                            if (int.Parse(a[i - 1].ToString()) == 0)
                            {
                                words = words + "Ten" + " ";
                            }
                            else
                            {
                                words = words + getNumberStringteen(int.Parse(a[i - 1].ToString())) + " ";
                            }

                            break;
                        }
                        else if (int.Parse(a[i - 1].ToString()) != 0)
                        {
                            words = words + getNumberString(int.Parse(a[i - 1].ToString())) + " ";
                            break;
                        }
                        else
                        {
                            break;
                        }
                    }
                    else
                    {
                        if (flag == 0)
                        {
                            for(int l=i;l>=0;l--)
                            {
                                if (int.Parse(a[l].ToString())!=0)
                                {
                                    lflag = 1;
                                }
                            }
                            if (lflag == 1 && int.Parse(a[i].ToString())!=0)
                            {

                                    words = words + getNumberString(int.Parse(a[i].ToString())) + " " + places[i] + " ";
                                    lflag = 0;


                            }
                            else if(lflag == 0)
                            {
                               // words = words + getNumberString(int.Parse(a[i].ToString())) + " " + places[i] + " ";
                                lflag = 0;
                                break;
                            }

                        }
                        else
                        {
                            words = words + " " + places[i] + " ";
                            flag = 0;
                        }

                    }
                }
            }
            Console.WriteLine(words);
        }
        static string getNumberString(int num)
        {
            string Word = String.Empty;
            switch (num)
            {
                case 1:
                    Word = "one";
                    break;
                case 2:
                    Word = "two";
                    break;

                case 3:
                    Word = "three";
                    break;

                case 4:
                    Word = "four";
                    break;

                case 5:
                    Word = "five";
                    break;

                case 6:
                    Word = "six";
                    break;
                case 7:
                    Word = "seven";
                    break;

                case 8:
                    Word = "eight";
                    break;

                case 9:
                    Word = "nine";
                    break;


            }
            return Word;
        }
        static string getNumberStringty(int num)
        {
            string Word = String.Empty;
            switch (num)
            {

                case 2:
                    Word = "twenty";
                    break;

                case 3:
                    Word = "thirty";
                    break;

                case 4:
                    Word = "fourty";
                    break;

                case 5:
                    Word = "fifty";
                    break;

                case 6:
                    Word = "sixty";
                    break;
                case 7:
                    Word = "seventy";
                    break;

                case 8:
                    Word = "eighty";
                    break;

                case 9:
                    Word = "ninty";
                    break;


            }
            return Word;
        }
        static string getNumberStringteen(int num)
        {
            string Word = String.Empty;
            switch (num)
            {
                    case 1:
                    Word = "eleven";
                    break;
                case 2:
                    Word = "tewlve";
                    break;

                case 3:
                    Word = "thirteen";
                    break;

                case 4:
                    Word = "fourteen";
                    break;

                case 5:
                    Word = "fifteen";
                    break;

                case 6:
                    Word = "sixteen";
                    break;
                case 7:
                    Word = "seventeen";
                    break;

                case 8:
                    Word = "eighteen";
                    break;

                case 9:
                    Word = "ninteen";
                    break;


            }
            return Word;
        }
    }

}

回答by Hannele

Fully recursive version:

完全递归版本:

private static string[] ones = {
    "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", 
    "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen",
};

private static string[] tens = { "zero", "ten", "twenty", "thirty", "forty", "fifty", "sixty", "seventy", "eighty", "ninety" };

private static string[] thous = { "hundred", "thousand", "million", "billion", "trillion", "quadrillion" };

private static string fmt_negative = "negative {0}";
private static string fmt_dollars_and_cents = "{0} dollars and {1} cents";
private static string fmt_tens_ones = "{0}-{1}"; // e.g. for twenty-one, thirty-two etc. You might want to use an en-dash or em-dash instead of a hyphen.
private static string fmt_large_small = "{0} {1}"; // stitches together the large and small part of a number, like "{three thousand} {five hundred forty two}"
private static string fmt_amount_scale = "{0} {1}"; // adds the scale to the number, e.g. "{three} {million}";

public static string ToWords(decimal number) {
    if (number < 0)
        return string.format(fmt_negative, ToWords(Math.Abs(number)));

    int intPortion = (int)number;
    int decPortion = (int)((number - intPortion) * (decimal) 100);

    return string.Format(fmt_dollars_and_cents, ToWords(intPortion), ToWords(decPortion));
}

private static string ToWords(int number, string appendScale = "") {
    string numString = "";
    // if the number is less than one hundred, then we're mostly just pulling out constants from the ones and tens dictionaries
    if (number < 100) {
        if (number < 20)
            numString = ones[number];
        else {
            numString = tens[number / 10];
            if ((number % 10) > 0)
                numString = string.Format(fmt_tens_ones, numString, ones[number % 10]);
        }
    } else {
        int pow = 0; // we'll divide the number by pow to figure out the next chunk
        string powStr = ""; // powStr will be the scale that we append to the string e.g. "hundred", "thousand", etc.

        if (number < 1000) { // number is between 100 and 1000
            pow = 100; // so we'll be dividing by one hundred
            powStr = thous[0]; // and appending the string "hundred"
        } else { // find the scale of the number
            // log will be 1, 2, 3 for 1_000, 1_000_000, 1_000_000_000, etc.
            int log = (int)Math.Log(number, 1000);
            // pow will be 1_000, 1_000_000, 1_000_000_000 etc.
            pow = (int)Math.Pow(1000, log);
            // powStr will be thousand, million, billion etc.
            powStr = thous[log];
        }

        // we take the quotient and the remainder after dividing by pow, and call ToWords on each to handle cases like "{five thousand} {thirty two}" (curly brackets added for emphasis)
        numString = string.Format(fmt_large_small, ToWords(number / pow, powStr), ToWords(number % pow)).Trim();
    }

    // and after all of this, if we were passed in a scale from above, we append it to the current number "{five} {thousand}"
    return string.Format(fmt_amount_scale, numString, appendScale).Trim();
}

Current works up to the (short scale) quadrillions. Additional support (for larger numbers, or for the long scale) can be added simply by changing the thousvariable.

当前的工作量高达(短规模)千万亿。可以简单地通过更改变量来添加额外的支持(对于更大的数字,或者对于长规模thous

回答by i3arnon

Currently the best, most robust, library for this is definitely Humanizer. It's open sourced and available as a nuget:

目前最好、最强大的库绝对是Humanizer。它是开源的,可以作为 nuget 使用:

Console.WriteLine(4567788.ToWords()); // => four million five hundred and sixty-seven thousand seven hundred and eighty-eight

It also has a wide range of tools solving the small problems every application has with strings, enums, DateTimes, TimeSpans and so forth, and supports many different languages.

它还具有广泛的工具来解决每个应用程序的小问题,包括strings、enums、DateTimes、TimeSpans 等等,并支持许多不同的语言。

Console.WriteLine(4567788.ToOrdinalWords().Underscore().Hyphenate().ApplyCase(LetterCasing.AllCaps)); // => FOUR-MILLION-FIVE-HUNDRED-AND-SIXTY-SEVEN-THOUSAND-SEVEN-HUNDRED-AND-EIGHTY-EIGHTH

回答by Elliot Wood

In case anyone wants a JavaScript version

如果有人想要 JavaScript 版本

Number.prototype.numberToWords = function () {
    var unitsMap = ["zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen"];
    var tensMap = ["zero", "ten", "twenty", "thirty", "forty", "fifty", "sixty", "seventy", "eighty", "ninety"];

    var num = this.valueOf();
    if (Math.round(num == 0)) {
        return "zero";
    }
    if (num < 0) {
        var positivenum = Math.abs(num);
        return "minus " + Number(positivenum).numberToWords();
    }
    var words = "";
    if (Math.floor(num / 1000000) > 0) {
        words += Math.floor(num / 1000000).numberToWords() + " million ";
        num = Math.floor(num % 1000000);
    }
    if (Math.floor(num / 1000) > 0) {
        words += Math.floor(num / 1000).numberToWords() + " thousand ";
        num = Math.floor(num % 1000);
    }
    if (Math.floor(num / 100) > 0) {
        words += Math.floor(num / 100).numberToWords() + " hundred ";
        num = Math.floor(num % 100);
    }
    if (Math.floor(num > 0)) {
        if (words != "") {
            words += "and ";
        }
        if (num < 20) {
        words += unitsMap[num];
        }
        else {
            words += tensMap[Math.floor(num / 10)];
            if ((num % 10) > 0) {
                words += "-" + unitsMap[Math.round(num % 10)];
            }
        }
    }
    return words.trim();
}

回答by Aamol

This class perfectly converts your float or double (till 2 precision). Just copy and paste in your IDE and see the result.

这个类完美地转换你的浮点数或双精度数(直到 2 精度)。只需复制并粘贴到您的 IDE 中即可查看结果。

class ConversionClass
{
    private static Dictionary<int, string> InitialNumbers = new Dictionary<int, string>();
    private static Dictionary<int, string> MultipleOfTen = new Dictionary<int, string>();
    private static Dictionary<int, string> MultipleOfHundered = new Dictionary<int, string>();

    private static void InitializeStatic()
    {
        //InitialNumbers.Add(0, "zero");
        InitialNumbers.Add(1, "one");
        InitialNumbers.Add(2, "two");
        InitialNumbers.Add(3, "three");
        InitialNumbers.Add(4, "four");
        InitialNumbers.Add(5, "five");
        InitialNumbers.Add(6, "six");
        InitialNumbers.Add(7, "seven");
        InitialNumbers.Add(8, "eight");
        InitialNumbers.Add(9, "nine");
        InitialNumbers.Add(10, "ten");
        InitialNumbers.Add(11, "eleven");
        InitialNumbers.Add(12, "tweleve");
        InitialNumbers.Add(13, "thirteen");
        InitialNumbers.Add(14, "fourteen");
        InitialNumbers.Add(15, "fifteen");
        InitialNumbers.Add(16, "sixteen");
        InitialNumbers.Add(17, "seventeen");
        InitialNumbers.Add(18, "eighteen");
        InitialNumbers.Add(19, "nineteen");

        MultipleOfTen.Add(1, "ten");
        MultipleOfTen.Add(2, "twenty");
        MultipleOfTen.Add(3, "thirty");
        MultipleOfTen.Add(4, "fourty");
        MultipleOfTen.Add(5, "fifty");
        MultipleOfTen.Add(6, "sixty");
        MultipleOfTen.Add(7, "seventy");
        MultipleOfTen.Add(8, "eighty");
        MultipleOfTen.Add(9, "ninety");

        MultipleOfHundered.Add(2, "hundred");                      //                100
        MultipleOfHundered.Add(3, "thousand");                     //              1 000
        MultipleOfHundered.Add(4, "thousand");                     //             10 000
        MultipleOfHundered.Add(5, "thousand");                     //            100 000
        MultipleOfHundered.Add(6, "million");                      //          1 000 000
        MultipleOfHundered.Add(7, "million");                      //        100 000 000
        MultipleOfHundered.Add(8, "million");                      //      1 000 000 000
        MultipleOfHundered.Add(9, "billion");                      //  1 000 000 000 000
    }

    public static void Main()
    {
        InitializeStatic();
        Console.WriteLine("Enter number :");
        var userInput = Console.ReadLine();
        double userValue ;
        if (double.TryParse(userInput, out userValue))  // userValue = 193524019.50
        {
            int decimalPortion = (int)userValue;
            //var fractionPortion = Math.Ceiling(((userValue < 1.0) ? userValue : (userValue % Math.Floor(userValue))) * 100);
            int fractionPortion = (int)(userValue * 100) - ((int)userValue * 100);

            int digit; int power;
            StringBuilder numberInText = new StringBuilder();

            while (decimalPortion > 0)
            {
                GetDigitAndPower(decimalPortion, out digit, out power);
                numberInText.Append(ConvertToText(ref decimalPortion, ref digit, ref power));
                if (decimalPortion > 0)
                {
                    decimalPortion = GetReminder(decimalPortion, digit, power);
                }
            }
            numberInText.Append(" point ");
            while (fractionPortion > 0)
            {
                GetDigitAndPower(fractionPortion, out digit, out power);
                numberInText.Append(ConvertToText(ref fractionPortion, ref digit, ref power));
                if (fractionPortion > 0)
                {
                    fractionPortion = GetReminder(fractionPortion, digit, power);
                }
            }

            Console.WriteLine(numberInText.ToString());
        }
        Console.ReadKey();
    }

    private static int GetReminder(int orgValue, int digit, int power)
    {
        int returningValue = orgValue - (digit * (int)Math.Pow(10, power));
        return returningValue;
    }

    private static void GetDigitAndPower(int originalValue, out int digit, out int power)
    {
        for (power = 0, digit = 0; power < 10; power++)
        {
            var divisionFactor = (int)Math.Pow(10, power);
            int operationalValue = (originalValue / divisionFactor);
            if (operationalValue <= 0)
            {
                power = power - 1;
                digit = (int)(originalValue / Math.Pow(10, power));
                break;
            }
        } 
    }

    private static string ConvertToText(ref int orgValue, ref int digit, ref int power)
    {
        string numberToText = string.Empty;

        if (power < 2)
        {
            if (InitialNumbers.ContainsKey(orgValue))
            {
                //This is for number 1 to 19
                numberToText = InitialNumbers[orgValue];
                orgValue = 0;
            }
            else if (MultipleOfTen.ContainsKey(digit))
            {
                //This is for multiple of 10 (20,30,..90)
                numberToText = MultipleOfTen[digit];
            }
        }
        else
        {
            if (power < 4)
            {
                numberToText = string.Format("{0} {1}", InitialNumbers[digit], MultipleOfHundered[power]);
            }
            else
            {
                StringBuilder sb = new StringBuilder();
                int multiplicationFactor = power / 3;
                int innerOrgValue = (int) (orgValue / Math.Pow(10, (multiplicationFactor * 3)));
                digit = innerOrgValue;
                var multiple = MultipleOfHundered[power];
                power = power - ((int)Math.Ceiling(Math.Log10(innerOrgValue)) - 1);

                int innerPower = 0;
                int innerDigit = 0;
                while (innerOrgValue > 0)
                {
                    GetDigitAndPower(innerOrgValue, out innerDigit, out innerPower);
                    var text = ConvertToText(ref innerOrgValue, ref innerDigit, ref innerPower);
                    sb.Append(text);
                    sb.Append(" ");
                    if (innerOrgValue > 0)
                    {
                        innerOrgValue = GetReminder(innerOrgValue, innerDigit, innerPower);
                    }
                }
                sb.Append(multiple);
                numberToText = sb.ToString();

            }
        }

        return numberToText + " ";
    }

}

回答by HaBo

Though this is kind of old question, I have implemented this functionality with more detailed approach

虽然这是一个老问题,但我已经用更详细的方法实现了这个功能

public static class NumberToWord
    {
        private static readonly Dictionary<long, string> MyDictionary = new Dictionary<long, string>();

        static NumberToWord()
        {
            MyDictionary.Add(1000000000000000, "quadrillion");
            MyDictionary.Add(1000000000000, "trillion");
            MyDictionary.Add(1000000000, "billion");
            MyDictionary.Add(1000000, "million");
            MyDictionary.Add(1000, "thousand");
            MyDictionary.Add(100, "hundread");
            MyDictionary.Add(90, "ninety");
            MyDictionary.Add(80, "eighty");
            MyDictionary.Add(70, "seventy");
            MyDictionary.Add(60, "sixty");
            MyDictionary.Add(50, "fifty");
            MyDictionary.Add(40, "fourty");
            MyDictionary.Add(30, "thirty");
            MyDictionary.Add(20, "twenty");
            MyDictionary.Add(19, "nineteen");
            MyDictionary.Add(18, "eighteen");
            MyDictionary.Add(17, "seventeen");
            MyDictionary.Add(16, "sixteen");
            MyDictionary.Add(15, "fifteen");
            MyDictionary.Add(14, "fourteen");
            MyDictionary.Add(13, "thirteen");
            MyDictionary.Add(12, "twelve");
            MyDictionary.Add(11, "eleven");
            MyDictionary.Add(10, "ten");
            MyDictionary.Add(9, "nine");
            MyDictionary.Add(8, "eight");
            MyDictionary.Add(7, "seven");
            MyDictionary.Add(6, "six");
            MyDictionary.Add(5, "five");
            MyDictionary.Add(4, "four");
            MyDictionary.Add(3, "three");
            MyDictionary.Add(2, "two");
            MyDictionary.Add(1, "one");
            MyDictionary.Add(0, "zero");
        }

        /// <summary>
        /// To the verbal.
        /// </summary>
        /// <param name="value">The value.</param>
        /// <returns></returns>
        public static string ToVerbal(this int value)
        {
            return ToVerbal((long) value);
        }

        /// <summary>
        /// To the verbal.
        /// </summary>
        /// <param name="value">The value.</param>
        /// <returns></returns>
        public static string ToVerbal(this long value)
        {
            if (value == 0) return MyDictionary[value];

            if (value < 0)
                return $" negative {ToVerbal(Math.Abs(value))}";

            var builder = new StringBuilder();

            for (var i = 1000000000000000; i >= 1000; i = i/1000)
                value = ConstructWord(value, builder, i);

            value = ConstructWord(value, builder, 100);

            for (var i = 90; i >= 20; i = i - 10)
                value = ConstructWordForTwoDigit(value, builder, i);

            if (MyDictionary.ContainsKey(value))
                builder.AppendFormat("{0}" + MyDictionary[value], builder.Length > 0 
                    ? " " 
                    : string.Empty);

            return builder.ToString();
        }

        private static long ConstructWord(long value, StringBuilder builder, long key)
        {
            if (value >= key)
            {
                var unit = (int) (value/key);
                value -= unit*key;
                builder.AppendFormat(" {0} {1} " + MyDictionary[key], builder.Length > 0
                    ? ", "
                    : string.Empty, ToVerbal(unit));
            }
            return value;
        }
        private static long ConstructWordForTwoDigit(long value, StringBuilder builder, long key)
        {
            if (value >= key)
            {
                value -= key;
                builder.AppendFormat(" {0} " + MyDictionary[key], builder.Length > 0
                    ? " "
                    : string.Empty);
            }
            return value;
        } 
    }

FYI: i have user string interpolation which is only available in 4.6.1

仅供参考:我有用户字符串插值,仅在 4.6.1 中可用

回答by Rustem Mustafin

Solution that takes up less code.

占用更少代码的解决方案。

The most important part is only couple lines:

最重要的部分只有几行:

static Func<long, string> remainder = t => t > 0 ? " " + ToEN(t) : "";

public static string ToEN(this long val, double d = 20, long th = 20)
{
    switch ((long)d)
    {
        case 20:   return val >= d ? ToEN(val, 1e2)             : en[val];
        case 100:  return val >= d ? ToEN(val, 1e3, 100)        : en[val / 10 * 10] + remainder(val % 10);
        default:   return val >= d ? ToEN(val, d * 1e3,(long)d) : ToEN(val / th) + " " + en[th] + remainder(val % th);
    }
}

Full code is available here https://dotnetfiddle.net/wjr4hF

完整代码可在此处获得https://dotnetfiddle.net/wjr4hF