Π§ΠΈΡ‚Π°ΠΉΡ‚Π΅ ΠΊΠ½ΠΈΠ³ΠΈ ΠΎΠ½Π»Π°ΠΉΠ½ Π½Π° Bookidrom.ru! БСсплатныС ΠΊΠ½ΠΈΠ³ΠΈ Π² ΠΎΠ΄Π½ΠΎΠΌ ΠΊΠ»ΠΈΠΊΠ΅

Π§ΠΈΡ‚Π°Ρ‚ΡŒ ΠΎΠ½Π»Π°ΠΉΠ½ Β«Linux ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ Π² ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π°Ρ…Β». Π‘Ρ‚Ρ€Π°Π½ΠΈΡ†Π° 126

Автор ΠΡ€Π½ΠΎΠ»ΡŒΠ΄ Роббинс

 animal = _("cat");

} else if (...) {

 ...

} else {

 ...

}

printf(_("the %s %s looks at you enquiringly.\n"), animal_color, color);

Π—Π΄Π΅ΡΡŒ Ρ„ΠΎΡ€ΠΌΠ°Ρ‚ΠΈΡ€ΡƒΡŽΡ‰Π°Ρ строка, animal_color ΠΈ animal Π½Π΅ΡƒΠ΄Π°Ρ‡Π½ΠΎ Π²ΠΊΠ»ΡŽΡ‡Π΅Π½Ρ‹ Π² Π²Ρ‹Π·ΠΎΠ² gettext(). Однако, послС ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Π° ΡƒΡ‚Π²Π΅Ρ€ΠΆΠ΄Π΅Π½ΠΈΠ΅ Π±ΡƒΠ΄Π΅Ρ‚ Π½Π΅Π²Π΅Ρ€Π½Ρ‹ΠΌ, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ порядок Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ΠΎΠ² Π½Π΅ ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ ΠΈΠ·ΠΌΠ΅Π½Π΅Π½ Π²ΠΎ врСмя исполнСния.

Π§Ρ‚ΠΎΠ±Ρ‹ ΠΎΠ±ΠΎΠΉΡ‚ΠΈ это, вСрсия сСмСйства printf() POSIX (Π½ΠΎ Π½Π΅ ISO Π‘) допускаСт ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Π² описатСлС Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Π° ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»ΡŒ полоТСния. Он ΠΏΡ€ΠΈΠ½ΠΈΠΌΠ°Π΅Ρ‚ Ρ„ΠΎΡ€ΠΌΡƒ дСсятичного числа, Π·Π° ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΌ слСдуСт символ $, сразу послС Π½Π°Ρ‡Π°Π»ΡŒΠ½ΠΎΠ³ΠΎ символа %. НапримСр printf("%2$s, %1s\n", "world", "hello");

Π£ΠΊΠ°Π·Π°Ρ‚Π΅Π»ΡŒ полоТСния ΠΎΠ±ΠΎΠ·Π½Π°Ρ‡Π°Π΅Ρ‚ Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ ΠΈΠ· списка, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ слСдуСт ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ, отсчСт начинаСтся с 1 ΠΈ Π½Π΅ Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ саму Ρ„ΠΎΡ€ΠΌΠ°Ρ‚ΠΈΡ€ΡƒΡŽΡ‰ΡƒΡŽ строку. Π­Ρ‚ΠΎΡ‚ ΠΏΡ€ΠΈΠΌΠ΅Ρ€ Π²Ρ‹Π²ΠΎΠ΄ΠΈΡ‚ Π·Π½Π°ΠΌΠ΅Π½ΠΈΡ‚ΠΎΠ΅ сообщСниС 'hello, world' Π² ΠΏΡ€Π°Π²ΠΈΠ»ΡŒΠ½ΠΎΠΌ порядкС.

GLIBC ΠΈ Solaris Ρ€Π΅Π°Π»ΠΈΠ·ΡƒΡŽΡ‚ эту Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎΡΡ‚ΡŒ. ΠŸΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ это Ρ‡Π°ΡΡ‚ΡŒ POSIX, Ссли printf() вашСго поставщика Unix Π½Π΅ Ρ€Π΅Π°Π»ΠΈΠ·ΡƒΠ΅Ρ‚ Π΅Π΅, ΠΎΠ½Π° вскорС Π΄ΠΎΠ»ΠΆΠ½Π° ΠΏΠΎΡΠ²ΠΈΡ‚ΡŒΡΡ.

Π—Π° ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»Π΅ΠΌ полоТСния ΠΌΠΎΠ³ΡƒΡ‚ ΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚ΡŒ Π»ΡŽΠ±Ρ‹Π΅ ΠΎΠ±Ρ‹Ρ‡Π½Ρ‹Π΅ Ρ„Π»Π°Π³ΠΈ printf(), ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»ΠΈ ΡˆΠΈΡ€ΠΈΠ½Ρ‹ ΠΏΠΎΠ»Π΅ΠΉ ΠΈ точности. Π’ΠΎΡ‚ ΠΏΡ€Π°Π²ΠΈΠ»Π° для использования ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»Π΅ΠΉ полоТСния:

β€’ Π€ΠΎΡ€ΠΌΠ° с ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»Π΅ΠΌ полоТСния Π½Π΅ ΠΌΠΎΠΆΠ΅Ρ‚ ΡΠΌΠ΅ΡˆΠΈΠ²Π°Ρ‚ΡŒΡΡ с Ρ„ΠΎΡ€ΠΌΠΎΠΉ Π±Π΅Π· Π½Π΅Π΅. Π”Ρ€ΡƒΠ³ΠΈΠΌΠΈ словами, ΠΈΠ»ΠΈ ΠΊΠ°ΠΆΠ΄Ρ‹ΠΉ ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»ΡŒ Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Π° Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»ΡŒ полоТСния, ΠΈΠ»ΠΈ Π½ΠΈ ΠΎΠ΄ΠΈΠ½ Π΅Π³ΠΎ Π½Π΅ Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚. ΠšΠΎΠ½Π΅Ρ‡Π½ΠΎ, %% ΠΌΠΎΠΆΠ΅Ρ‚ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒΡΡ всСгда.

β€’ Π•сли Π² Ρ„ΠΎΡ€ΠΌΠ°Ρ‚ΠΈΡ€ΡƒΡŽΡ‰Π΅ΠΉ строкС ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ N-ΠΉ Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚, Π² этой строкС Π΄ΠΎΠ»ΠΆΠ½Ρ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒΡΡ Ρ‚Π°ΠΊΠΆΠ΅ всС Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚Ρ‹ Π΄ΠΎ N. БоотвСтствСнно, ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅Π΅ Π½Π΅Π²Π΅Ρ€Π½ΠΎ printf("%3$s %1$s\n", "hello", "cruel", "world");

β€’ Π‘сылка Π½Π° ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π½Ρ‹ΠΉ Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ сдСлана ΡƒΠΊΠ°Π·Π°Ρ‚Π΅Π»Π΅ΠΌ полоТСния нСсколько Ρ€Π°Π·. НС ΠΏΠΎΠ·ΠΈΡ†ΠΈΠΎΠ½Π½Ρ‹Π΅ спСцификаторы Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Π° всСгда двиТутся Ρ‡Π΅Ρ€Π΅Π· список Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ΠΎΠ² ΠΏΠΎΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎ.

Π­Ρ‚Π° Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎΡΡ‚ΡŒ Π½Π΅ ΠΏΡ€Π΅Π΄Π½Π°Π·Π½Π°Ρ‡Π΅Π½Π° для нСпосрСдствСнного использования программистами ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠΉ, ΠΎΠ½Π° скорСС для ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρ‡ΠΈΠΊΠΎΠ². НапримСр, ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅ΠΉ Ρ„ΠΎΡ€ΠΌΠ°Ρ‚ΠΈΡ€ΡƒΡŽΡ‰Π΅ΠΉ строки, "The %s %s looks at you enquiringly.\n", Π½Π° французский ΠΌΠΎΠ³ Π±Ρ‹ Π±Ρ‹Ρ‚ΡŒ:

"Le %2$s %1$s te regarde d'un aire interrogateur.\n"

(Π”Π°ΠΆΠ΅ этот ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ Π½Π΅ ΡΠΎΠ²Π΅Ρ€ΡˆΠ΅Π½Π΅Π½: Π°Ρ€Ρ‚ΠΈΠΊΠ»ΡŒ Β«LeΒ» ΠΈΠΌΠ΅Π΅Ρ‚ Ρ€ΠΎΠ΄. ΠŸΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΊΠ° ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ ΠΊ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρƒ трудная Π·Π°Π΄Π°Ρ‡Π°!)

13.3.6. ВСстированиС ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ² Π² ΠΏΠ΅Ρ€ΡΠΎΠ½Π°Π»ΡŒΠ½ΠΎΠΌ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³Π΅

ΠšΠΎΠ»Π»Π΅ΠΊΡ†ΠΈΡ сообщСний Π² ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ΅ называСтся списком сообщСний (message catalog). Π­Ρ‚ΠΎΡ‚ Ρ‚Π΅Ρ€ΠΌΠΈΠ½ примСняСтся Ρ‚Π°ΠΊΠΆΠ΅ ΠΊ ΠΊΠ°ΠΆΠ΄ΠΎΠΌΡƒ ΠΈΠ· ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ² сообщСний Π½Π° Π΄Ρ€ΡƒΠ³ΠΎΠΉ язык. Когда ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ° установлСна, ΠΊΠ°ΠΆΠ΄Ρ‹ΠΉ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ Ρ‚Π°ΠΊΠΆΠ΅ устанавливаСтся Π² стандартноС мСсто, Π³Π΄Π΅ gettext() ΠΌΠΎΠΆΠ΅Ρ‚ Π²ΠΎ врСмя исполнСния Π½Π°ΠΉΡ‚ΠΈ Π½ΡƒΠΆΠ½Ρ‹ΠΉ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄.

ΠœΠΎΠΆΠ΅Ρ‚ ΠΎΠΊΠ°Π·Π°Ρ‚ΡŒΡΡ ΠΏΠΎΠ»Π΅Π·Π½Ρ‹ΠΌ Ρ€Π°Π·ΠΌΠ΅ΡΡ‚ΠΈΡ‚ΡŒ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρ‹ Π½Π΅ Π² стандартном, Π° Π² Π΄Ρ€ΡƒΠ³ΠΎΠΌ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³Π΅, особСнно для тСстирования ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹. ОсобСнно Π½Π° Π±ΠΎΠ»ΡŒΡˆΠΈΡ… систСмах, Ρƒ ΠΎΠ±Ρ‹Ρ‡Π½ΠΎΠ³ΠΎ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»Ρ ΠΌΠΎΠΆΠ΅Ρ‚ Π½Π΅ Π±Ρ‹Ρ‚ΡŒ Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΡ‹Ρ… Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½ΠΈΠΉ для установки Ρ„Π°ΠΉΠ»ΠΎΠ² Π² систСмныС ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³ΠΈ. Ѐункция bindtextdomain() Π΄Π°Π΅Ρ‚ gettext() Π°Π»ΡŒΡ‚Π΅Ρ€Π½Π°Ρ‚ΠΈΠ²Π½ΠΎΠ΅ мСсто для поиска ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ²:

#include <libintl.h> /* GLIBC */


char *bindtextdomain(const char *domainname,

const char *dirname);

ΠŸΠΎΠ»Π΅Π·Π½Ρ‹Π΅ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³ΠΈ Π²ΠΊΠ»ΡŽΡ‡Π°ΡŽΡ‚ '.' для Ρ‚Π΅ΠΊΡƒΡ‰Π΅Π³ΠΎ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³Π° ΠΈ /tmp. ΠœΠΎΠΆΠ΅Ρ‚ ΠΎΠΊΠ°Π·Π°Ρ‚ΡŒΡΡ ΡƒΠ΄ΠΎΠ±Π½Ρ‹ΠΌ Ρ‚Π°ΠΊΠΆΠ΅ ΠΏΠΎΠ»ΡƒΡ‡ΠΈΡ‚ΡŒ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³ ΠΈΠ· ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΠΎΠΉ окруТСния, ΠΏΠΎΠ΄ΠΎΠ±Π½ΠΎ этому:

char *td_dir;

setlocale(LC_ALL, "");

textdomain("killerapp");

if ((td_dir = getenv("KILLERAPP_TD_DIR")) != NULL)

 bindtextdomain("killerapp", td_dir);

bindtextdomain() Π΄ΠΎΠ»ΠΆΠ½Π° Π±Ρ‹Ρ‚ΡŒ Π²Ρ‹Π·Π²Π°Π½Π° Π΄ΠΎ Π²Ρ‹Π·ΠΎΠ²ΠΎΠ² любой ΠΈΠ· Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΉ ΠΈΠ· сСмСйства gettext(). ΠœΡ‹ ΡƒΠ²ΠΈΠ΄ΠΈΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€ Π΅Π΅ использования Π² Ρ€Π°Π·Π΄Π΅Π»Π΅ 13.3.8 Β«Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ²Β»

13.3.7. ΠŸΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΊΠ° ΠΈΠ½Ρ‚Π΅Ρ€Π½Π°Ρ†ΠΈΠΎΠ½Π°Π»ΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Π½Π½Ρ‹Ρ… ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌ

К настоящСму ΠΌΠΎΠΌΠ΅Π½Ρ‚Ρƒ ΠΌΡ‹ рассмотрСли всС ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹, ΠΈΠ· ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… состоит интСрнационализированная ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ°. Π”Π°Π½Π½Ρ‹ΠΉ Ρ€Π°Π·Π΄Π΅Π» ΠΏΠΎΠ΄Π²ΠΎΠ΄ΠΈΡ‚ ΠΈΡ‚ΠΎΠ³ΠΈ.

1. Π’ΠΊΠ»ΡŽΡ‡ΠΈΡ‚Π΅ Π² своС ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅ Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ» gettext.h, Π΄ΠΎΠ±Π°Π²ΡŒΡ‚Π΅ опрСдСлСния для макросов _() ΠΈ N_() Π² Π·Π°Π³ΠΎΠ»ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ», ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ΡΡ Π²ΠΎ всС ваши исходныС Ρ„Π°ΠΉΠ»Ρ‹ Π½Π° Π‘. НС Π·Π°Π±ΡƒΠ΄ΡŒΡ‚Π΅ ΠΎΠΏΡ€Π΅Π΄Π΅Π»ΠΈΡ‚ΡŒ ΠΈΠΌΠ΅Π½ΠΎΠ²Π°Π½Π½ΡƒΡŽ константу ENABLE_NLS.

2. Π’Ρ‹Π·ΠΎΠ²ΠΈΡ‚Π΅ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ setlocale(). ΠŸΡ€ΠΎΡ‰Π΅ всСго Π²Ρ‹Π·Π²Π°Ρ‚ΡŒ 'setlocale(LC_ALL, "")', Π½ΠΎ ΠΈΠ½ΠΎΠ³Π΄Π° ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΡŽ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΠΎΡ‚Ρ€Π΅Π±ΠΎΠ²Π°Ρ‚ΡŒΡΡ Π±Ρ‹Ρ‚ΡŒ Π±ΠΎΠ»Π΅Π΅ Ρ€Π°Π·Π±ΠΎΡ€Ρ‡ΠΈΠ²Ρ‹ΠΌ Π² ΠΎΡ‚Π½ΠΎΡˆΠ΅Π½ΠΈΠΈ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌΡ‹Ρ… ΠΊΠ°Ρ‚Π΅Π³ΠΎΡ€ΠΈΠΉ Π»ΠΎΠΊΠ°Π»ΠΈ.

3. Π’Ρ‹Π±Π΅Ρ€ΠΈΡ‚Π΅ для прилоТСния тСкстовый Π΄ΠΎΠΌΠ΅Π½ ΠΈ установитС Π΅Π³ΠΎ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ textdomain().

4. ΠŸΡ€ΠΈ тСстировании свяТитС тСкстовый Π΄ΠΎΠΌΠ΅Π½ с ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π½Ρ‹ΠΌ ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³ΠΎΠΌ ΠΏΡ€ΠΈ ΠΏΠΎΠΌΠΎΡ‰ΠΈ bindtextdomain().

5. Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ strfmon(), strftime() ΠΈ Ρ„Π»Π°Π³ '. Если Π½ΡƒΠΆΠ½Π° другая информация ΠΎ Π»ΠΎΠΊΠ°Π»ΠΈ, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ nl_langinfo(), особСнно Π² сочСтании с strftime().

6. ΠŸΠΎΠΌΠ΅Ρ‚ΡŒΡ‚Π΅ всС строки, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ Π±Ρ‹Ρ‚ΡŒ ΠΏΠ΅Ρ€Π΅Π²Π΅Π΄Π΅Π½Ρ‹, ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΌΠΈ Π²Ρ‹Π·ΠΎΠ²Π°ΠΌΠΈ _() ΠΈΠ»ΠΈ N_().

Π₯отя Π½Π΅ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π½Π΅ слСдуСт Ρ‚Π°ΠΊ ΠΏΠΎΠΌΠ΅Ρ‡Π°Ρ‚ΡŒ. НапримСр, Ссли Π²Ρ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚Π΅ getopt_long() (см. Ρ€Π°Π·Π΄Π΅Π» 2.1.2 Β«Π”Π»ΠΈΠ½Π½Ρ‹Π΅ ΠΎΠΏΡ†ΠΈΠΈ GNUΒ»), Π²Ρ‹, вСроятно, Π½Π΅ Π·Π°Ρ…ΠΎΡ‚ΠΈΡ‚Π΅, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΈΠΌΠ΅Π½Π° Π΄Π»ΠΈΠ½Π½Ρ‹Ρ… ΠΎΠΏΡ†ΠΈΠΉ Π±Ρ‹Π»ΠΈ ΠΏΠΎΠΌΠ΅Ρ‡Π΅Π½Ρ‹ для ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Π°. НС Ρ‚Ρ€Π΅Π±ΡƒΡŽΡ‚ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Π° ΠΈ простыС Ρ„ΠΎΡ€ΠΌΠ°Ρ‚ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ строки Π½Π°ΠΏΠΎΠ΄ΠΎΠ±ΠΈΠ΅ "%d %d\n", Ρ‚Π°ΠΊΠΆΠ΅ ΠΊΠ°ΠΊ ΠΎΡ‚Π»Π°Π΄ΠΎΡ‡Π½Ρ‹Π΅ сообщСния.

7. Π’ Π½ΡƒΠΆΠ½Ρ‹Ρ… мСстах ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ ngettext() (ΠΈΠ»ΠΈ Π΅Π΅ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚Ρ‹) для Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ ΠΌΠΎΠ³ΡƒΡ‚ Π±Ρ‹Ρ‚ΡŒ 1 ΠΈΠ»ΠΈ большС 1.

8. Π£ΠΏΡ€ΠΎΡΡ‚ΠΈΡ‚Π΅ Тизнь для своих ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρ‡ΠΈΠΊΠΎΠ², ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ строки с ΠΏΠΎΠ»Π½Ρ‹ΠΌΠΈ прСдлоТСниями вмСсто Π·Π°ΠΌΠ΅Π½Ρ‹ слов с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ %s ΠΈ ?:. НапримСр:

if (/* Π²ΠΎΠ·Π½ΠΈΠΊΠ»Π° ошибка */) { /* Π’Π•Π ΠΠž */

 /* Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ нСсколько строк для упрощСния ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Π°. */

 if (input_type == INPUT_FILE)

  fprintf(stderr, _("%s: cannot read file: %s\n"),

   argv[0], strerror(errno));

 else

  fprintf(stderr, _("%s: cannot read pipe: %s\n"),

   argv[0], strerror(errno));

Π­Ρ‚ΠΎ Π»ΡƒΡ‡ΡˆΠ΅, Ρ‡Π΅ΠΌ

if (/* Π²ΠΎΠ·Π½ΠΈΠΊΠ»Π° ошибка */) { /* ΠΠ•Π’Π•Π ΠΠž */

 fprintf(stderr, _("%s: cannot read %s: %s\n"), argv[0],

 input_type == INPUT_FILE ? _("file") : _("pipe"),

 strerror(errno));

}

Как Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Ρ‡Ρ‚ΠΎ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ, Ρ…ΠΎΡ€ΠΎΡˆΠ΅ΠΉ ΠΌΡ‹ΡΠ»ΡŒΡŽ являСтся Π²ΠΊΠ»ΡŽΡ‡Π΅Π½ΠΈΠ΅ коммСнтария, ΡΠΎΠΎΠ±Ρ‰Π°ΡŽΡ‰Π΅Π³ΠΎ ΠΎ Π½Π°ΠΌΠ΅Ρ€Π΅Π½Π½ΠΎΠΌ использовании Π½Π΅ΡΠΊΠΎΠ»ΡŒΠΊΠΈΡ… строк, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΡƒΠΏΡ€ΠΎΡΡ‚ΠΈΡ‚ΡŒ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ сообщСний.

13.3.8. Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ²

ПослС ΠΈΠ½Ρ‚Π΅Ρ€Π½Π°Ρ†ΠΈΠΎΠ½Π°Π»ΠΈΠ·Π°Ρ†ΠΈΠΈ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡ‹ Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΠΎ ΠΏΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΈΡ‚ΡŒ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρ‹. Π­Ρ‚ΠΎ осущСствляСтся с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Π½Π΅ΡΠΊΠΎΠ»ΡŒΠΊΠΈΡ… инструмСнтов уровня ΠΎΠ±ΠΎΠ»ΠΎΡ‡ΠΊΠΈ. ΠœΡ‹ Π½Π°Ρ‡Π½Π΅ΠΌ с ΠΈΠ½Ρ‚Π΅Ρ€Π½Π°Ρ†ΠΈΠΎΠ½Π°Π»ΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Π½Π½ΠΎΠΉ вСрсии ch06-echodate.c ΠΈΠ· Ρ€Π°Π·Π΄Π΅Π»Π° 6.1.4 Β«ΠŸΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΠΎΠ²Π°Π½ΠΈΠ΅ Ρ€Π°Π·Π»ΠΎΠΆΠ΅Π½Π½ΠΎΠ³ΠΎ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ Π² time_tΒ»:

/* ch13-echodate.c --- дСмонстрация ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ² */

#include <stdio.h>

#include <time.h>

#include <locale.h>

#define ENABLE_NLS 1

#include "gettext.h"

#define _(msgid) gettext(msgid)

#define N_(msgid) msgid


int main (void) {

 struct tm tm;

 time_t then;


 setlocale(LC_ALL, "");

 bindtextdomain("echodate", ".");

 textdomain("echodate");


 printf("%s", _("Enter a Date/time as YYYY/MM/DD HH:MM:SS : "));

 scanf("%d/%d/%d %d:%d:%d",

  &tm.tm_year, &tm.tm_mon, &tm.tm_mday,

  &tm.tm_hour, &tm.tm_min, &tm.tm_sec);


 /* ΠŸΡ€ΠΎΠ²Π΅Ρ€ΠΊΠ° ошибок для краткости ΠΎΠΏΡƒΡ‰Π΅Π½Π°. */

 tm.tm_year -= 1900;

 tm.tm_mon -= 1;

 tm.tm_isdst = -1; /* О Π»Π΅Ρ‚Π½Π΅ΠΌ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ Π½ΠΈΡ‡Π΅Π³ΠΎ Π½Π΅ извСстно */


 then = mktime(&tm);

 printf(_("Got: %s"), ctime(&then));

 exit(0);

}

ΠœΡ‹ Π½Π°ΠΌΠ΅Ρ€Π΅Π½Π½ΠΎ использовали "gettext.h", Π° Π½Π΅ <gettext.h>. Если нашС ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅ поставляСтся с ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½ΠΎΠΉ ΠΊΠΎΠΏΠΈΠ΅ΠΉ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠΈ gettext, Ρ‚ΠΎΠ³Π΄Π° "gettext.h" Π½Π°ΠΉΠ΄Π΅Ρ‚ Π΅Π΅, ΠΈΠ·Π±Π΅ΠΆΠ°Π² использования систСмной ΠΊΠΎΠΏΠΈΠΈ. Π‘ Π΄Ρ€ΡƒΠ³ΠΎΠΉ стороны, Ссли имССтся лишь систСмная копия, ΠΎΠ½Π° Π±ΡƒΠ΄Π΅Ρ‚ Π½Π°ΠΉΠ΄Π΅Π½Π°, Ссли локальной ΠΊΠΎΠΏΠΈΠΈ Π½Π΅Ρ‚. ΠžΠ±Ρ‰Π΅ΠΈΠ·Π²Π΅ΡΡ‚Π½ΠΎ, Ρ‡Ρ‚ΠΎ ситуация услоТнСна Ρ„Π°ΠΊΡ‚ΠΎΠΌ наличия Π½Π° систСмах Solaris Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠΈ gettext, которая Π½Π΅ ΠΈΠΌΠ΅Π΅Ρ‚ всСх возмоТностСй вСрсии GNU.

ΠŸΠ΅Ρ€Π΅Ρ…ΠΎΠ΄Ρ ΠΊ созданию ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΎΠ², ΠΏΠ΅Ρ€Π²Ρ‹ΠΌ шагом являСтся ΠΈΠ·Π²Π»Π΅Ρ‡Π΅Π½ΠΈΠ΅ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΈΠΌΡ‹Ρ… строк. Π­Ρ‚ΠΎ осущСствляСтся ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠΎΠΉ xgettext:

$ xgettext --keyword=_ --keyword=N_ \

> --default-domain=echodate ch13-echodate.с

ΠžΠΏΡ†ΠΈΠΈ --keyword сообщаСт xgettext, Ρ‡Ρ‚ΠΎ Π½ΡƒΠΆΠ½ΠΎ ΠΈΡΠΊΠ°Ρ‚ΡŒ макросы _() ΠΈ N_(). ΠŸΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ° ΡƒΠΆΠ΅ Π·Π½Π°Π΅Ρ‚, ΠΊΠ°ΠΊ ΠΈΠ·Π²Π»Π΅ΠΊΠ°Ρ‚ΡŒ строки ΠΈΠ· gettext() ΠΈ Π΅Π΅ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ΠΎΠ², Π° Ρ‚Π°ΠΊΠΆΠ΅ ΠΈΠ· gettext_noop().

Π’Ρ‹Π²ΠΎΠ΄ xgettext называСтся пСрСносимым ΠΎΠ±ΡŠΠ΅ΠΊΡ‚Π½Ρ‹ΠΌ Ρ„Π°ΠΉΠ»ΠΎΠΌ. Имя Ρ„Π°ΠΉΠ»Π° ΠΏΠΎ ΡƒΠΌΠΎΠ»Ρ‡Π°Π½ΠΈΡŽ messages.Ρ€ΠΎ, Ρ‡Ρ‚ΠΎ соотвСтствуСт тСкстовому Π΄ΠΎΠΌΠ΅Π½Ρƒ ΠΏΠΎ ΡƒΠΌΠΎΠ»Ρ‡Π°Π½ΠΈΡŽ "messages". ΠžΠΏΡ†ΠΈΡ --default-domain ΠΎΠ±ΠΎΠ·Π½Π°Ρ‡Π°Π΅Ρ‚ тСкстовый Π΄ΠΎΠΌΠ΅Π½ для использования Π² ΠΈΠΌΠ΅Π½ΠΈ Π²Ρ‹Ρ…ΠΎΠ΄Π½ΠΎΠ³ΠΎ Ρ„Π°ΠΉΠ»Π°. Π’ Π΄Π°Π½Π½ΠΎΠΌ случаС, Ρ„Π°ΠΉΠ» Π½Π°Π·Π²Π°Π½ echodate.Ρ€ΠΎ. Π’ΠΎΡ‚ Π΅Π³ΠΎ содСрТаниС:

# SOME DESCRIPTIVE TITLE. /* Π¨Π°Π±Π»ΠΎΠ½, Π½ΡƒΠΆΠ½ΠΎ ΠΎΡ‚Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ */

# Copyright (Π‘) YEAR THE PACKAGE'S COPYRIGHT HOLDER