установить LC_ *, но не LC_ALL

13

Я хотел бы иметь немецкий (Австрия) языковой стандарт (формат бумаги A4, 24 часа, гггг-мм-дд), но англоязычный пользовательский интерфейс (я не люблю плохие переводы). Я решил, что правильный способ добиться этого - установить LC_переменные следующим образом .bashrc(пожалуйста, исправьте меня, если я ошибаюсь):

LC_MESSAGES=en_US.UTF-8
LC_$everythingelse=de_AT.UTF-8

Есть ли более элегантный способ установить LC_ $ everythingelse вместо установки каждого отдельного значения? Установка LC_ALL не является опцией, так как она имеет приоритет над LC_MESSAGES:

$ export LC_ALL=de_AT.UTF_8
$ export LC_MESSAGES=en_US.UTF_8
$ echo $LC_MESSAGES
en_US.UTF_8
$ locale | grep LC_MESSAGES
LC_MESSAGES="de_AT.UTF_8"

PS: Это общая машина, и я не sudoer, поэтому изменение общесистемных настроек не вариант.

Heinzi
источник

Ответы:

15

Существует три набора настроек локали¹:

  • LANGзапасной вариант, если вы не указали значение для категории. Пользователи могут указывать свой язык простым способом.
  • LC_xxxдля каждой категории ( xxxможет быть MESSAGES, TIMEи т. д.).
  • LC_ALLпереопределяет все настройки. Это способ для приложений переопределить все настройки для работы в известной локали (обычно Cв локали по умолчанию), обычно так, чтобы различные команды производили вывод в известном формате.

Таким образом, вы можете установить LANG=de_AT.UTF-8и LC_MESSAGES=C( Cявляется языковым стандартом по умолчанию и означает, что он не переведен; en_USобычно идентичен Cдля сообщений).

Однако есть две категории, в которых я не рекомендую менять значение по умолчанию, потому что оно ломает множество программ:

  • LC_COLLATEпорядок сопоставления символов Это не очень полезно, потому что оно показывает только, как сортировать символы, а не как сортировать строки. Инструменты, которые умеют сортировать строки, не используют LC_COLLATE. Более того, многие инструменты ожидают таких вещей, как « [a-z]соответствует всем 26 строчным буквам ASCII и никаким другим символам ASCII», но это не так в большинстве языков, отличных от заданных по умолчанию (попробуйте echo B | LC_COLLATE=en_US grep '[a-z]').
  • LC_NUMERICуказывает, как отображать цифры. В частности, во многих языках это позволяет использовать числа с плавающей запятой ,вместо .десятичной точки. Но большинство программ, которые разбирают числа, ожидают a .и рассматривают ,как разделитель полей.

Поэтому я рекомендую

  • либо явно LC_COLLATE=C LC_NUMERIC=_C,
  • или оставить LANGотключенными и только установить значение для полезных категорий ( LC_MESSAGES, LC_TIME, LC_PAPER, плюс LC_CTYPE(стоимость которого может изменяться в зависимости от вашего терминала)).

¹ Плюс LANGUAGEс GNU libc. Если вы не слышали об этом, вы не пропустите много.

Жиль "ТАК - перестань быть злым"
источник
Спасибо за подробный ответ и пояснения! Я попробую локализованный LC_NUMERIC, хотя, поскольку цифровая клавиатура на немецкой клавиатуре имеет ,место вместо .(к сожалению), поэтому ввод цифр с точкой неудобен (и большинство приложений, кажется, хорошо работают с нестандартным LC_NUMERIC). Я не полностью понимаю ваш пример LC_COLLATE: в моей системе приведенный вами пример не совпадает B.
Хайнци
@ Heinzi Влияет ли (должно) LC_COLLATE на диапазоны символов?
Жиль "ТАК - перестань быть злым"
10

Человек страница локали (7) говорит:

локаль по умолчанию [...] определяется с помощью следующих шагов:

  1. Если существует переменная окружения с ненулевым значением LC_ALL, используется значение LC_ALL.

  2. Если переменная среды с тем же именем, что и у одной из категорий [LC_ *] выше, существует и не равна нулю, ее значение используется для этой категории.

  3. Если переменная окружения ненулевая LANG, используется значение LANG.

Таким образом, вы можете использовать LANG как своего рода аналог LC_ALL с низким приоритетом: установите для LANG значение, de_ATа для LC_MESSAGES en_US:

$ env LC_MESSAGES=en_US.UTF-8 LANG=de_AT.UTF-8 locale | egrep '(MESSAGES|PAPER)'
LC_MESSAGES=en_US.UTF-8
LC_PAPER="de_AT.UTF-8"
Риккардо Мурри
источник