我有3个资源包(RB)属性文件:RB_en, RB_fr and RB
。我将默认语言环境设置为“en_US
”,现在我使用getBundle("RB", new Locale("fr"))
获取键“ key1 ”的值。我知道Java首先会查找属性文件RB_fr,但是如果在RB_fr
中找不到密钥“ key1 ”,那么它将继续查找哪个oder? RB_en
文件或RB
文件?
所以这里有一些演示代码:
RB.properties: key1 = valueRB
RB_en.properties: key1 = valueRB_en
RB_fr.properties:key2 = valueRB_fr
Locale fr = new Locale("fr");
Locale.setDefault(new Locale("en", "US"));
ResourceBundle b = ResourceBundle.getBundle("RB", fr);
b.getString("key1");
我读了一本书,OCP Java SE 8 Programmer II,它说订单将是RB_fr -> RB_en -> RB
。但是当我进行测试时,它显示的顺序是RB_fr -> RB
,RB_en
甚至没有考虑到。所以这让我有点困惑,任何人都可以解释一下哪个订单是正确的吗?
答案 0 :(得分:2)
您必须区分缺少捆绑和缺少密钥。
您首先使用getBundle
请求法语资源包。这个查找确实如本书和相应的javadoc中所述:
getBundle使用基本名称,指定的区域设置和默认值 locale(从Locale.getDefault获取)生成一个序列 候选包名称。
...
getBundle然后迭代候选包名称,找到第一个可以实例化实际资源包的名称。
由于RB_fr.properties
存在,它将找到并实例化。
然后,您正在使用getString
请求密钥key1
的值。但除了getBundle
之外,这并没有回退到默认语言环境。它只查看当前的包和任何父母:
从此资源包或其父项之一获取给定键的字符串。
法语包的父级是基础包(即RB.properties
),这解释了为什么你没有看到英文值(父链也在下面详细解释了上面链接了getBundle
的javadoc。)
如果您是例如,您会观察到预期的行为。寻找德国资源包:
ResourceBundle b = ResourceBundle.getBundle("RB", new Locale("de"));
b.getString("key1"); // valueRB_en
在这种情况下,getBundle
找不到任何RB_de.properties
并回退到RB_en.properties
,其中key1
存在并将被返回。