# 55.2.对于程序员来说
# 55.2.1.机械师
本节介绍如何在属于PostgreSQL发行版的程序或库中实现本机语言支持。目前,它只适用于C程序。
向程序添加NLS支持
将以下代码插入程序的启动顺序:
#ifdef ENABLE_NLS #include <locale.h> #endif ... #ifdef ENABLE_NLS setlocale(LC_ALL, ""); bindtextdomain("progname", LOCALEDIR); textdomain("progname"); #endif
(小标题)*
程序名
*实际上可以自由选择。)无论在哪里找到一条可供翻译的信息,都可以拨打
gettext()
需要插入。例如。:fprintf(stderr, "panic level %d\n", lvl);
将更改为:
fprintf(stderr, gettext("panic level %d\n"), lvl);
(
gettext
如果未配置NLS支持,则定义为无操作。)这往往会增加很多混乱。一个常见的快捷方式是使用:
#define _(x) gettext(x)
另一种解决方案是可行的,如果程序通过一个或几个功能进行大部分通信,例如
ereport()
在后端。然后进行这个函数调用gettext
在所有的输入字符串上。添加一个文件
nls。mk
在包含程序源的目录中。此文件将作为makefile读取。这里需要进行以下变量分配:目录名称
程序名,如
textdomain()
呼叫使用语言
提供的翻译列表-最初为空。
GETTEXT_文件
包含可翻译字符串的文件列表,即标记为
gettext
或者另一种解决方案。最终,这将包括该程序的几乎所有源文件。如果这个列表太长,你可以将第一个“文件”设为+
第二个单词是每行包含一个文件名的文件。GETTEXT_触发器
为翻译人员生成消息目录的工具需要知道哪些函数调用包含可翻译字符串。默认情况下,只有
gettext()
电话是已知的。如果你用过_
或者你需要在这里列出的其他标识符。如果可翻译字符串不是第一个参数,则该项的形式必须相同func:2
(对于第二个论点)。如果您有一个支持复数消息的函数,那么该项应该如下所示func:1,2
(识别单数和复数消息参数)。构建系统将自动构建和安装消息目录。
# 55.2.2.信息写作指南
下面是一些编写易于翻译的消息的指南。
不要在运行时构造句子,比如:
printf("Files were %s.\n", flag ? "copied" : "removed");
在其他语言中,句子中的词序可能不同。而且,即使你记得打电话
gettext()
在每个片段上,这些片段可能无法很好地单独翻译。最好复制一点代码,这样每个要翻译的消息都是一个连贯的整体。在运行时,只应将数字、文件名等运行时变量插入到消息文本中。出于类似的原因,这是行不通的:
printf("copied %d file%s", n, n!=1 ? "s" : "");
因为它假设复数是如何形成的。如果你认为你可以这样解决它:
if (n==1) printf("copied 1 file"); else printf("copied %d files", n):
那就失望吧。有些语言有两种以上的形式,有一些特殊的规则。通常,最好设计消息以完全避免问题,例如:
printf("number of copied files: %d", n);
如果你真的想构建一个适当的多元信息,有人支持这一点,但这有点尴尬。在中生成主要或详细错误消息时
ereport()
,你可以这样写:errmsg_plural("copied %d file", "copied %d files", n, n)
第一个参数是适用于英语单数形式的格式字符串,第二个参数是适用于英语复数形式的格式字符串,第三个参数是决定使用哪种复数形式的整数控制值。后续参数按照格式字符串进行格式化,与往常一样。(通常,复数化控制值也是要格式化的值之一,因此必须写入两次。)在英语中,重要的是*
n
是1或不是1,但在其他语言中可能有许多不同的复数形式。翻译人员将两个英文表单视为一个整体,有机会提供多个替换字符串,并根据n
*.如果你需要将一条不会直接发送给客户的信息多元化
嗯
或错误细节
报告时,必须使用底层函数ngettext
.请参阅gettext文档。如果您想与译者交流一些信息,例如关于消息如何与其他输出对齐,请在字符串出现之前添加以开头的注释
翻译
,例如:/* translator: This message is not what it seems to be. */
这些注释会复制到邮件目录文件中,以便翻译人员可以看到它们。