Java 如何使用真正的多语言字符串制作应用程序?

Java 如何使用真正的多语言字符串制作应用程序?,java,android,multilingual,Java,Android,Multilingual,为不同语言生成字符串的最佳方法是什么?我有这个问题,我试图显示字符串,如“月”、“月”、“年”、“年”。目前我正在学习三种我知道的语言:西班牙语、英语和波兰语。对于英语和西班牙语,这是直截了当的。但例如,在波兰语中,“年”可以变成“lata”(在数字2-4之后)或“lat”(在数字5之后)。我正在考虑为它添加一个额外的字符串,并在其他语言中使其为空。然而,这让我想到了我不懂的其他语言,它们可能会有更多的差异。如果我考虑将来添加更多语言,在这种情况下,哪种方法应该是最好的方法?听起来您想要一种,或

为不同语言生成字符串的最佳方法是什么?我有这个问题,我试图显示字符串,如“月”、“月”、“年”、“年”。目前我正在学习三种我知道的语言:西班牙语、英语和波兰语。对于英语和西班牙语,这是直截了当的。但例如,在波兰语中,“年”可以变成“lata”(在数字2-4之后)或“lat”(在数字5之后)。我正在考虑为它添加一个额外的字符串,并在其他语言中使其为空。然而,这让我想到了我不懂的其他语言,它们可能会有更多的差异。如果我考虑将来添加更多语言,在这种情况下,哪种方法应该是最好的方法?

听起来您想要一种,或者至少通过使用一种:

publicstaticvoidmain(字符串…参数){
字符串[]格式={
//注意-在真正的应用程序中,您可以从一种语言获取格式字符串,
//文件,而不是在程序中硬编码。显然。

{0,数字}{0,choice,0#years | 1#years | 1请注意,我没有任何特定于android的经验……但我通常会选择为我要支持的每种语言提供单独的视图文件,这允许比单独的语言更广泛的本地化,如果您知道其他语言的文本可能需要,您现在也可以稍微修改布局,例如广域r按钮,甚至不同的图像。

有一个内置的“复数”支持,但没有很好的文档记录。

提到了,你可以在中看到。

多亏了我得到的答案,我正在写两个基于Android的解决方案。我使用的第一个解决方案是复数。第一眼查看复数文档/示例,你可能会认为有一个quantity=“level”(对于2-4个复数)仅在区域设置“cs”上进行检查。对于其他区域设置,只有“one”和“other”起作用。 因此,在strings.xml文件中:

<plurals name ="years">
    <item quantity="one">1 year</item>
    <item quantity="other"><xliff:g id="number">%d</xliff:g> years</item>
</plurals>

一年
%d年
因此,对于波兰语,我会:

<plurals name ="years">
    <item quantity="one">1 rok</item>
    <item quantity="other"><xliff:g id="number">%d</xliff:g> lat</item>
</plurals>

1韩国
%德拉特
然后我会在我的代码上:

int n = getYears(...);
if (Locale.getDefault().getLanguage().equalsIgnoreCase("pl") && n >= 2 && n <= 4) {
   return getString(R.string.years_pl, n);
} else {
   return getResources().getQuantityString(R.plurals.years, n, n);
}
...
private static final int LANG_PL = 0;
// add more languages here if needed
...
String formats[] = {
"{0,number} {0,choice,1#" + getString(R.string.year_1) + "|2#" + getString(R.string.years_2_4) +  "|4<" + getString(R.string.years_lots) +"}", // polish
// more to come
};
...
// Here I would add more for certain languages
    if (Locale.getDefault().getLanguage().equalsIgnoreCase("pl")) {
       return MessageFormat.format(formats[LANG_PL], n);
    } else {
       return getResources().getQuantityString(R.plurals.years, n, n);
    }
int n=getYears(…);

if(Locale.getDefault().getLanguage().equalsIgnoreCase(“pl”)&&n>=2&&n请注意,我希望您正在使用清单字符串文件,对于您的问题:您指的是运行时的情况,您选择了语言?如果是这样,我认为使用localizion的反射将帮助您,而无需询问您的用户…是的,我正在使用字符串文件。但是我不知道是否可以使用字符串文件以干净的方式显示我想要的内容。是的,它是关于在运行时显示某些消息,更具体地说是关于处理复数,在某些语言中,复数可以有不止一种写入方式。谢谢,我想这正是我需要的!你知道使用xliff和不使用xliff的区别吗?在其中一个链接中,他们使用以下内容:%s他们使用的另一个方面是:%d匹配尝试后,它似乎不支持这样的内容(我需要这个,因为在波兰语中,数量从2到4的复数形式与其他形式不同).有什么方法可以做到这一点吗?我自己不使用这个,你需要搜索Android资源以获取示例。正如我在前面的评论中所说的,不要使用复数,它们不支持“零”“。使用Android可以做到这一点。如何处理需要在运行时设置的字符串?我在运行时需要做的事情相当有限,但我通过自己的一些类方法使用“普通”i18n表,如
String::stringWithLocalizedString('Good{timeofday}{username}'))
等可用于格式化功能的解决方案。感谢您的示例,起初我正在寻找一种更基于android的解决方案(例如,仅使用xml来生成字符串),所以说实话,我认为将Android字符串系统与ChoiceFormat集成是不可能的,但你刚刚给了我一个如何将两者混合的好主意。顺便说一句,这正是我想要的,在某些数字之后复数的变化。唯一的警告是,添加具有特殊复数变化的新语言需要修改源代码的详细说明。这当然不是办法。请将字符串放在/res/string中的参考资料文件中。但最好使用ChoiceFormat而不是thna复数,因为这里的代码示例仅用于说明如何使用
ChoiceFormat
。我不建议您硬编码语言字符串。Edited代码澄清。我真的不明白你为什么要费心混合复数和
MessageFormat
?如果我是你,我会尝试找出只使用复数的正确方法,或者我会完全放弃复数,只对所有语言使用
MessageFormat
——比如说
MessageFormat.format(getString(R.string.year_format),n)
似乎比你现在拥有的要容易得多。是的,我想你是对的,我将只使用MessageFormat。我只是不想扔掉复数代码。我不能只使用复数(这将是最好的)。谢谢你的帮助:)不要使用复数。它们被窃听了。
<string name="years_pl"><xliff:g id="number">%d</xliff:g> lata</string>
...
private static final int LANG_PL = 0;
// add more languages here if needed
...
String formats[] = {
"{0,number} {0,choice,1#" + getString(R.string.year_1) + "|2#" + getString(R.string.years_2_4) +  "|4<" + getString(R.string.years_lots) +"}", // polish
// more to come
};
...
// Here I would add more for certain languages
    if (Locale.getDefault().getLanguage().equalsIgnoreCase("pl")) {
       return MessageFormat.format(formats[LANG_PL], n);
    } else {
       return getResources().getQuantityString(R.plurals.years, n, n);
    }