Разница между CurrentCulture, InvariantCulture, CurrentUICulture и InstalledUICulture

В чем разница между CurrentCulture, InvariantCulture, CurrentUICulture а также InstalledUICulture от System.Globalization.CultureInfo?

2 ответа

Решение

Я бы попытался дать более глубокий ответ, чем этот.

CurrentCulture следует использовать для форматирования. То есть числа, валюты, проценты, даты и время всегда должны быть отформатированы в соответствии с этой культурой, прежде чем их отобразить пользователю. Несколько примеров здесь:

const string CURRENCY_FORMAT = "c";
const string PERCENTAGE_FORMAT = "p";

DateTime now = DateTime.UtcNow; // all dates should be kept in UTC internally
// convert time to local and format appropriately for end user
dateLabel.Text = now.ToLocalTime().ToString(CultureInfo.CurrentCulture);

float someFloat = 12.3456f;
// yields 12,3456 for pl-PL Culture
floatLabel.Text = someFloat.ToString(CultureInfo.CurrentCulture);
// yields 12,35 zł for pl-PL Culture - rounding takes place!
currencyLabel.Text = someFloat.ToString(CURRENCY_FORMAT, CultureInfo.CurrentCulture);
// yields 1234,56% for pl-PL Culture - 1.0f is 100%
percentageLabel.Text = someFloat.ToString(PERCENTAGE_FORMAT, CultureInfo.CurrentCulture);

Важно отметить, что вы никогда не должны использовать float ни double для хранения информации, связанной с валютой, в первую очередь (decimal это правильный выбор).
Другой общий случай использования CurrentCulture анализ с учетом локали. Ваше приложение всегда должно позволять пользователям вводить данные в своем региональном формате:

float parsedFloat;
if (float.TryParse(inputBox.Text, NumberStyles.Float, CultureInfo.CurrentCulture, out parsedFloat))
{
    MessageBox.Show(parsedFloat.ToString(CultureInfo.CurrentCulture), "Success at last!");
}

Обратите внимание, что я всегда предоставляю IFormatProvider параметр, хотя он подразумевается и предполагается, что CultureInfo.CurrentCulture, Причина в том, что я хочу общаться с коллегами-разработчиками: это то, что будет отображаться для конечных пользователей. Это одна из причин, почему FxCop рассматривает пропуск этого параметра как ошибку.


InvariantCulture, с другой стороны, должен использоваться для надежного преобразования одного из классов, упомянутых выше, в его текстовое представление. Так что если вы хотите, например, передать DateTime, float, double или аналогичный объект через сеть, сохраните его в базе данных или какой-либо текстовый файл (включая XML), вы всегда должны использовать InvariantCulture:

float someFloat = 1234.56f;
// yields 1234.56
string internalFloat = someFloat.ToString(CultureInfo.InvariantCulture);
DateTime now = DateTime.UtcNow;
// yields something like 04/16/2011 19:02:46
string internalDateAndTime = now.ToString(CultureInfo.InvariantCulture);

Следует отметить, что формат даты / времени, предлагаемый InvariantCulture на самом деле точно так же, как en-US. Хотя это надежно, это не совсем правильно. Что действительно нужно использовать, так это ISO8601 сменный формат даты и времени. По какой-то причине Microsoft даже не предоставляет такой шаблон (наиболее близкими являются шаблон Sortable - "s" и универсальный шаблон - "u", который напоминает только формат ISO8601), вам необходимо создать свой собственный файл следующим образом:

const string iso8601Pattern = "yyyy-MM-dd'T'HH:mm:ss'Z'";
string iso8601Formatted = now.ToString(iso8601Pattern);

Довольно важное примечание: IFormatProvider здесь действительно требуется, так как пропуск этого параметра может привести к серьезным ошибкам. Однажды мне пришлось исправить дефект на французской ОС. Код был такой:

float dbVersion = // some kind of logic that took float from database
string versionString = dbVersion.ToString(); // culture-aware formatting used
Version ver = new Version(versionString); // exception thrown here

Причина была очень простой: форматирование с плавающей запятой на французской ОС (с французским региональным форматированием) было отформатировано примерно на 10,5 и Version Класс требует культурально-инвариантного ввода.


CurrentUICulture отвечает за загрузку соответствующих переводимых ресурсов для вашего приложения. То есть его следует использовать для отображения правильных текстовых сообщений, цветов и изображений.
В приложении Asp.Net, если вы хотите по какой-то причине реализовать механизм локализации CSS (возможность переопределять определения CSS для каждого языка), CurrentUICulture хороший способ пойти (при условии, что вы действительно читаете это свойство из веб-браузера).
Аналогично, если вы хотите реализовать механизм переключения языков, CurrentUICulture это тот, который должен быть переопределен.


InstalledUICulture подключено к локали интерфейса пользователя по умолчанию для ОС. Как говорится в MSDN:

Это свойство является эквивалентом GetSystemDefaultUILanguage в Windows API.

Чтобы действительно понять, что это за свойство, нам нужно углубиться в некоторую теорию. Существуют разные линейки продуктов Windows:

  • один язык (например, английский, французский, немецкий, японский и т. д.)
  • MUI (многоязычный пользовательский интерфейс - английская базовая ОС и языковые пакеты)

Для одноязычных продуктовых линеек InstalledUICulture всегда будет возвращать язык операционной системы, тогда как для MUI он всегда должен возвращать английский (США) aka en-US. Это полезно? Я не знаю, мне никогда не нужна была такая информация. И лично я не видел программу, которая бы использовала это свойство.

Взято из этого ответа:

CurrentCulture - это.NET-представление языка пользователя системы по умолчанию. Это контролирует число по умолчанию, форматирование даты и тому подобное.

CurrentUICulture относится к языку пользовательского интерфейса по умолчанию - настройке, введенной в Windows 2000. Это в первую очередь касается части локализации / перевода пользовательского интерфейса вашего приложения.

Независимо от региональных параметров, в которых настроена система, это будут "текущие" значения в вашем.NET-приложении.

Часто они оба одинаковы. Но в моей системе они были бы другими: я предпочитаю свои цифры и даты в немецком формате, поэтому CurrentCulture будет немецким, но я также предпочитаю все свои приложения на английском языке, поэтому CurrentUICulture будет английским.

Другие вопросы по тегам