在Python中,有没有一种简单而优先的方式来格式化德语数字字符串?

4

我正在寻找在Windows操作系统下用Python进行德国数字格式化(例如1.000,1234)的正确方法。

我尝试了locale.setlocale,但没有成功。

相反,我编写了一个函数来得到所需的输出。

有更好的方法吗?

def ger_num(number, precision=3):
    """
    returns german formatted number as string or an empty string
    """
    if number is not None:
        try:
            my_number = "{:,f}".format(number)
        except ValueError:
            return ""

        decimals, fraction = my_number.split(".")[0], my_number.split(".")[1]
        decimals = decimals.replace(",", ".")

        if precision:
            return decimals + "," + fraction[:precision]
        else:
            return decimals

    else:
        return ""

请提供对您的输入和输出的清晰描述。 - SuperKogito
你用 locale 尝试了什么?也许你的平台不支持它?在这里查看许多答案:https://dev59.com/1WYq5IYBdhLWcg3wridD - juanpa.arrivillaga
4个回答

5

您可以使用 locale.setlocale 将语言环境设置为 de,然后使用 locale.format 格式化数字:

import locale
locale.setlocale(locale.LC_ALL, 'de')
print(locale.format('%.4f', 1000.1234, 1))

这将输出:
1.000,1234

1
在Debian上,你可能想要通过运行“locale -a”来检查你特定的区域标识符,如果缺失则查看“man locale-gen”。我使用的是“de_DE.utf8”。此外,在Python 3.7中已废弃“locale.format”,请改用“locale.format_string()”。 - felixhummel

4
如果由于某些原因您无法使用locale(或者不想使用),那么最简单的其他选择可能是使用字符串替换,就像这个已经提到的答案建议的那样(它从PEP-378中获取答案)。
您可以始终将其封装在一个函数中,例如:
def format_number(number, precision=3):
    # build format string
    format_str = '{{:,.{}f}}'.format(precision)

    # make number string
    number_str = format_str.format(number)

    # replace chars
    return number_str.replace(',', 'X').replace('.', ',').replace('X', '.')

对于intfloatDecimal,这个方法效果很好:

最初的回答:

>>> format_number(1)
'1,000'
>>> format_number(1, 2)
'1,00'
>>> format_number(1, 7)
'1,0000000'
>>> format_number(1234567, 7)
'1.234.567,0000000'

>>> format_number(1234567.9988, 7)
'1.234.567,9988000'
>>> format_number(1234567.9988, 2)
'1.234.568,00'

>>> from decimal import Decimal
>>> format_number(Decimal('1234567.9988'), 2)
'1.234.568,00'
>>> format_number(Decimal('1234567.9988'), 5)
'1.234.567,99880'
>>> format_number(Decimal('1234567.9988'), 0)
'1.234.568'
>>> format_number(Decimal('123456'), 5)
'123.456,00000'

我成功地将这个函数编辑成了一些能够让我在欧元格式货币前面显示欧元符号的东西——比担心本地化问题要好得多。 - RozzA

0
感谢帮助。如果有人发现这个有用,我在这里提供我的最终解决方案代码。

ger_num.py:

def ger_num(number, digits=2):
    '''
    retruns <number> as german formattet string (thousands-.),
    rounds to n <digits>.

    <number> == None OR (!= INT AND != FLOAT) returns '' (empty STR)
    '''
    import locale
    locale.setlocale(locale.LC_ALL, 'de')
    if number is None:
        return ''
    if not isinstance(number, int) and not isinstance(number, float):
        return ''
    else:
        format = '%.'+str(digits)+'f'
        return locale.format_string(format, number, 1)


if __name__ == "__main__":
    pass

0
如果locale再次出现问题,我建议使用简单的字符串替换。上面提到的format_number函数很好,但它并不总是保留输入。例如,format_number(Decimal('1234567.9988'), 0)会将英文转换为德文格式,但会删除小数点后的数字。一个简单而安全的方法是将任何英文字符串数字转换为德文字符串数字。
de_number = number.replace(".", "$DECIMAL$")
de_number = de_number.replace(",", ".")
de_number = de_number.replace("$DECIMAL$", ",")

从帖子中我了解到输入的数字始终为正数,但如果可能为负数,可以使用number[1:]代替number。如果大部分输入数字为负数,可能值得使用locale,它似乎默认处理这些数字。
要将输入的德语字符串数字格式化为英语字符串数字而不再改变输入,请使用:
en_number = number.replace(",", "$DECIMAL$")
en_number = en_number.replace(".", ",")
en_number = en_number.replace("$DECIMAL$", ".")

如果en_number没有千位分隔符,只有小数点,现在可以像在Python中一样正确使用它,例如float(en_number)。例如,float("5000.0")是有效的,但是德语等效的float("5000,0")会导致ValueError错误。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接