如何从它在 Java 中的字符串表示中获得语言环境?

有没有一种简单的方法可以从 Locale 的 toString()方法返回的“编程名称”中获得一个 地点实例?一个明显而丑陋的解决方案是解析 String,然后根据它构造一个新的 Locale 实例,但是也许有更好的方法/现成的解决方案?

我需要在 SQL 数据库中存储一些特定于语言环境的设置,包括语言环境本身,但是将序列化的语言环境对象放在那里会很难看。我更愿意存储它们的 String 表示形式,这些表示形式在细节上似乎相当充分。

161430 次浏览

这似乎没有一个静态的 valueOf方法,这有点令人惊讶。

一种相当丑陋但简单的方法是迭代 Locale.getAvailableLocales(),将它们的 toString值与您的值进行比较。

不是很好,但是不需要字符串解析。您可以预先填充字符串到 Locales 的 Map,并在该 Map 中查找数据库字符串。

查看 Locale.getLanguage()Locale.getCountry()... 存储在数据库中的组合,而不是 "programatic name"..。
如果要重新构建语言环境,请使用 public Locale(String language, String country)

下面是一个示例代码:)

// May contain simple syntax error, I don't have java right now to test..
// but this is a bigger picture for your algo...
public String localeToString(Locale l) {
return l.getLanguage() + "," + l.getCountry();
}


public Locale stringToLocale(String s) {
StringTokenizer tempStringTokenizer = new StringTokenizer(s,",");
if(tempStringTokenizer.hasMoreTokens())
String l = tempStringTokenizer.nextElement();
if(tempStringTokenizer.hasMoreTokens())
String c = tempStringTokenizer.nextElement();
return new Locale(l,c);
}

好吧,我会存储一个字符串串联的 Locale.getISO3Language()getISO3Country()和 getVariant ()作为键,这将允许我后来调用 Locale(String language, String country, String variant)构造函数。

事实上,依赖 displayLanguage 意味着使用 locale 语言来显示它,这使得它与 iso 语言代码相反,依赖于 locale。

例如,en locale 键可以存储为

en_EN
en_US

诸如此类。

老问题有很多答案,但这里有更多的解决方案:

返回 locale 的方法存在于 commons-lang 库中: LocaleUtils.toLocale(localeAsString)

因为我刚刚实施了:

Groovy/Grails中,应该是:

def locale = Locale.getAvailableLocales().find { availableLocale ->
return availableLocale.toString().equals(searchedLocale)
}

从 Java7开始,就有了使用 IETF 语言标记的工厂方法 Locale.forLanguageTag和实例方法 Locale.toLanguageTag

这个答案可能有点晚,但是解析出字符串并不像 OP 假设的那样难看。我发现它非常简单明了:

public static Locale fromString(String locale) {
String parts[] = locale.split("_", -1);
if (parts.length == 1) return new Locale(parts[0]);
else if (parts.length == 2
|| (parts.length == 3 && parts[2].startsWith("#")))
return new Locale(parts[0], parts[1]);
else return new Locale(parts[0], parts[1], parts[2]);
}

我使用 Locale.toString ()文档中给出的所有示例(在 Java7上)对此进行了测试: “ en”、“ de _ DE”、“ _ GB”、“ en _ US _ WIN”、“ de _ _ POSIX”、“ zh _ CN _ # Hans”、“ zh _ TW _ # Hant-x-Java”和“ th _ TH _ TH _ # u-nu-thai”。

重要更新 : 根据 文件,这不推荐在 Java7 + 中使用:

特别是,将 toString 的输出解析为语言、国家和变量字段的客户机可以继续这样做(尽管这是 非常气馁) ,但是如果存在脚本或扩展,变量字段中将包含额外的信息。

改为使用 Locale.forLanguageTag 和 Locale.toLanguageTag,如果必须使用 Locale.Builder,也可以使用 Locale.Builder。

你可以在安卓系统上使用,对我来说很好用。

private static final Pattern localeMatcher = Pattern.compile
("^([^_]*)(_([^_]*)(_#(.*))?)?$");


public static Locale parseLocale(String value) {
Matcher matcher = localeMatcher.matcher(value.replace('-', '_'));
return matcher.find()
? TextUtils.isEmpty(matcher.group(5))
? TextUtils.isEmpty(matcher.group(3))
? TextUtils.isEmpty(matcher.group(1))
? null
: new Locale(matcher.group(1))
: new Locale(matcher.group(1), matcher.group(3))
: new Locale(matcher.group(1), matcher.group(3),
matcher.group(5))
: null;
}
  1. Java 提供了很多东西,通过适当的实现可以避免很多复杂性。

    String key = "ms-MY";
    Locale locale = new Locale.Builder().setLanguageTag(key).build();
    
  2. Apache Commons has LocaleUtils to help parse a string representation. This will return en_US

    String str = "en-US";
    Locale locale =  LocaleUtils.toLocale(str);
    System.out.println(locale.toString());
    
  3. You can also use locale constructors.

    // Construct a locale from a language code.(eg: en)
    new Locale(String language)
    // Construct a locale from language and country.(eg: en and US)
    new Locale(String language, String country)
    // Construct a locale from language, country and variant.
    new Locale(String language, String country, String variant)
    

Please check this LocaleUtils and this Locale to explore more methods.

选项1:

org.apache.commons.lang3.LocaleUtils.toLocale("en_US")

选项2:

Locale.forLanguageTag("en-US")

请注意,选择一在语言和国家之间是“下划线”,而 选择二是“破折号”。

如果你在你的项目中使用 Spring 框架,你也可以使用:

org.springframework.util.StringUtils.parseLocaleString("en_US");

文件 :

将给定的 String 表示形式解析为区域设置

可能会迟到,但是如果有人想要一个简单的解决方案:

通过使用: String langTag = localeObj.toLanguageTag();代替 toString()设置语言环境字符串

langTag存储在 DB 或任何您想要的地方

在消费者方面得到 String lanTag = fromDB(); // or wherever

通过 Locale locale = Locale.forLanguageTag(langTag);获取现场

不需要额外的依赖!