Android复数治疗“零”

如果在我的strings.xml中有以下复数的资源:

<plurals name="item_shop"> <item quantity="zero">No item</item> <item quantity="one">One item</item> <item quantity="other">%d items</item> </plurals> 

我将结果显示给用户使用:

 textView.setText(getQuantityString(R.plurals.item_shop, quantity, quantity)); 

它与1及以上的运作良好,但如果数量为0,那么我看到“0项”。 文件似乎表明只有阿拉伯文支持“零”价值吗? 还是我错过了什么?

国际化的Android资源方法非常有限。 我使用标准的java.text.MessageFormat获得了更好的成功。

基本上,你所要做的就是使用像这样的标准string资源:

 <resources> <string name="item_shop">{0,choice,0#No items|1#One item|1&lt;{0} items}</string> </resources> 

然后,从代码你所要做的是以下几点:

 String fmt = getResources().getText(R.string.item_shop).toString(); textView.setText(MessageFormat.format(fmt, amount)); 

您可以阅读更多关于MessageFormat的javadoc中的格式化string

http://developer.android.com/guide/topics/resources/string-resource.html#Plurals

请注意,select是基于语法的必要性。 即使数量为0,由于0在语法上不同于2,或者除1之外的任何其他数字(“零书本”,“一本书”,“两本书”等等)上)。 不要被这样一个事实所误导,比如说,两个声音只能用于数量2:一种语言可能要求2,12,102(等等)都是相互对待的,但是与其他的不同数量。 依靠你的翻译,以了解他们的语言实际上坚持什么区别。

总之,“零”只用于某些语言(“两个”很less,等等),因为其他语言没有特殊的共轭,因此“零”字段被认为是不必要的

Android正在使用CLDR复数系统,这只是不是如何工作(所以不要指望这会改变)。

系统描述如下:

http://cldr.unicode.org/index/cldr-spec/plural-rules

总之,理解“one”并不意味着数字1是重要的。相反,这些关键字是类别,属于每个类别的具体数字n是由CLDR数据库中的规则定义的:

http://unicode.org/repos/cldr-tmp/trunk/diff/supplemental/language_plural_rules.html

虽然似乎没有任何语言使用“0”以外的任何东西0,有语言赋予0“1”。 当然,有很多情况下,“两”包含的其他数字不只是2。

如果Android在哪里允许你做你想做的事情,那么你的应用程序就不能被正确地翻译成任意数量的具有更复杂复杂规则的语言。

这里是我用来解决这个问题,而不切换到MessageFormat的解决方法。

首先,我将“零”string提取到它自己的string资源中。

 <string name="x_items_zero">No items.</string> <plurals name="x_items"> <!-- NOTE: This "zero" value is never accessed but is kept here to show the intended usage of the "zero" string --> <item quantity="zero">@string/x_items_zero</item> <item quantity="one">One item.</item> <item quantity="other">%d items.</item> </plurals> 

然后在我自己的ResourcesUtil中有一些方便的方法

 public static String getQuantityStringZero(Resources resources, int resId, int zeroResId, int quantity) { if (quantity == 0) { return resources.getString(zeroResId); } else { return resources.getQuantityString(resId, quantity, quantity); } } public static String getQuantityStringZero(Resources resources, int resId, int zeroResId, int quantity, Object... formatArgs) { if (quantity == 0) { return resources.getString(zeroResId); } else { return resources.getQuantityString(resId, quantity, formatArgs); } } 

现在任何时候我想使用一个特定的string数量为零我打电话:

 String pluralString = ResourcesUtil.getQuantityStringZero( getContext().getResources(), R.plural.x_items, R.string.x_items_zero, quantity ); 

我希望有更好的东西,但至less可以完成这项工作,同时保持string资源的XML清晰。

如果你正在使用数据绑定,你可以用下面的方法解决这个问题:

 <TextView ... android:text="@{collection.size() > 0 ? @plurals/plural_str(collection.size(), collection.size()) : @string/zero_str}"/>