【问题标题】:PHP NumberFormatter Slovenian spellout wrongPHP NumberFormatter 斯洛文尼亚语拼写错误
【发布时间】:2013-11-24 20:08:48
【问题描述】:

我正在尝试使用 intl 包中的 NumberFormatter 类将整数数量拼写为斯洛文尼亚语单词(用于邮政声明),但结果完全错误且毫无意义。

$fmt = new NumberFormatter('sl', NumberFormatter::SPELLOUT);
$fmt->format(561);

结果为“petsto šestdeset ena”,而它应该是“petsto enainšestdeset”。看起来像婴儿说话。

在非常相似的克罗地亚语中,结果似乎还可以(“petsto šezdeset i jedan”)。

这是在 PHP 中做的不好的翻译还是基于我的系统语言环境?我在 PHP 5.3.10 / Ubuntu 12.04 上。

编辑:

intl是1.1.0版本,现在是3.0.0,可能已经修复了?

【问题讨论】:

  • 翻译由 PHP intl 扩展提供。以我的经验,有些事情不时出错,并在后续版本中得到修复。我在 PHP/5.5.5 / Windows 7 中得到了相同的结果,所以这可能是一个错误。
  • Álvaro 感谢您对其进行测试。我不认为这是一个错误,而只是一些尚未完成的事情,例如在“dvjesto devetdeset šest”中,这个“dvjesto”甚至不是斯洛文尼亚语单词,而且总是在十位之前,我认为这在斯拉夫语言中是独一无二的。我将在 PHP 错误系统上报告此问题。
  • 即使在 5.5.5 版本上,它看起来也像婴儿谈话:petsto šestdeset ena。您可能必须找到替代库或编写自己的库。
  • @Glavić 你能用 phpinfo() 检查你有哪个国际版本?我无法为我的 5.3.10 提交报告,因为应该只报告 5.4 或 5.5 的错误,所以我会像使用你的系统一样报告。
  • @OmerSabic: intl 版本是 1.1.0,ICU 版本是 51.2

标签: php intl


【解决方案1】:

免责声明 - 我不会说斯洛文尼亚语或克罗地亚语。

PHP 扩展用于这些语言中的数字的模式似乎存在一些差距。要明白我的意思,您可以通过运行显示使用的模式:

$fmt = new NumberFormatter('sl', NumberFormatter::SPELLOUT);
echo $fmt->getPattern();

如果您查看此输出,您可能会发现“%spellout-cardinal-masculine:”的一部分似乎从大约 30 跳到了 100。

...
    21: dvaset >%spellout-cardinal-masculine>;
    30: <%spellout-cardinal-masculine<deset;
    31: <%spellout-cardinal-masculine<deset >%spellout-cardinal-masculine>;
    100: sto;
    101: sto >%spellout-cardinal-masculine>;
    200: dvjesto;
...

这意味着没有为大于 31 和小于 100 的数字定义规则。您输出的数字的 '61' 部分属于此间隙。

您可以生成自己的模式来解决这个问题 - 我粘贴了 en-US 格式化程序的模式并稍微调整了一下,所以它看起来像这样:

...
    21: dvaset >%spellout-cardinal-masculine>;
    30: <%spellout-cardinal-masculine<deset;
    31: <%spellout-cardinal-masculine<deset >%spellout-cardinal-masculine>;
    40: forty;
    41: forty->%spellout-cardinal-masculine>;
    50: fifty;
    51: fifty->%spellout-cardinal-masculine>;
    60: sixty;
    61: sixty->%spellout-cardinal-masculine>;
    70: seventy;
    71: seventy->%spellout-cardinal-masculine>;
    80: eighty;
    81: eighty->%spellout-cardinal-masculine>;
    90: ninety;
    91: ninety->%spellout-cardinal-masculine>;
    100: sto;
    101: sto >%spellout-cardinal-masculine>;
    200: dvjesto;
...

现在,如果我将它保存在一个名为 sl.txt 且采用 UTF-8 编码的新文件中,我可以将它加载到 NumberFormatter 中:

$pattern = file_get_contents('sl.txt')
$fmt = new NumberFormatter('sl', NumberFormatter::PATTERN_RULEBASED, $pattern);
echo($fmt->format(561));

这给了我以下输出:

petsto sixty-ena

当然,这是错误的 - 它是斯洛文尼亚语和英语的混合体,但我认为如果您将格式编辑成这样:

...
    61: >%spellout-cardinal-masculine>inšestdeset;
...

正如我所说,我不会说斯洛文尼亚语,所以你可能想检查一下。但这会给你以下输出:

petsto enainšestdeset

您需要为从 31 到 100 的每个缺失的数字块添加此规则。您可能还想检查ICU docs for rule based formatting 以确保您得到正确。

这是一个错误,但不是在 PHP 中 - 如果您想修复它,那么问题在 this 文件中的 Unicode's Common Locale Data Repository 中。 PHP 的 intl 使用 ICU,它使用 CLDR 数据。

【讨论】:

  • 喂。那时,我最终推出了自己的斯洛文尼亚语拼写功能。然而我还是欠你的。我已经对规则集进行了修复,但小数点给我带来了问题:如果我用规则集加载NumberFormatter,构造函数会失败。这是造成问题的那一行(在阳性下)x.x: &lt;&lt; vejica &gt;%spellout-cardinal-feminine&gt;; 如果我从中删除%spellout-cardinal-feminine,没关系(但拼写错误)。这是整个规则集:tauron.si/sl.txt
猜你喜欢
  • 2011-10-19
  • 2012-02-01
  • 1970-01-01
  • 2012-01-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多