[英]How to create a formatted localized string?
我有一个本地化的字符串,需要采取一些变量。 但是,在本地化中,变量的顺序可能会因语言而异。
所以这不是一个好主意:
NSString *text = NSLocalizedString(@"My birthday is at %@ %@ in %@", nil);
在某些语言中,某些词语出现在其他语言之前,而在其他语言中则是相反的。 我目前缺乏一个很好的例子。
如何在格式化字符串中提供NAMED变量? 没有一些沉重的自制字符串替换,有没有办法做到这一点? 即使是一些编号变量,如{%@ 1},{%@ 2}等也足够......是否有解决方案?
这就是NSLocalizedString
采用两个参数的原因。 使用第二个参数包含描述变量的本机语言含义的注释。 然后,翻译人员可以使用$
+数字结构重新排序它们。 请参阅Apple的Localizing Notes 。
但是,您不能跳过一种语言的参数。 例如,如果您有3个英语参数和4个法语参数,并且您不需要英语中的第三个参数,则不能格式化为%1$@ %2$@ and %4$@
。 你只能跳过最后一个。
格式化本地化字符串示例:
NSString *today = [MyHandWatch today];
NSString *msg = [NSString stringWithFormat:NSLocalizedString(@"Today is %@", @""), today];
genstrings将在Localizable.strings文件中生成此行:
"Today is %@" = "Today is %@";
几个星期前,我通过使用NSScanner
构建自己的简单模板系统解决了这个问题。 该方法使用模板系统查找具有语法${name}
变量。 变量通过NSDictionary
提供给方法。
- (NSString *)localizedStringFromTemplateString:(NSString *)string variables:(NSDictionary *)variables {
NSMutableString *result = [NSMutableString string];
// Create scanner with the localized string
NSScanner *scanner = [[NSScanner alloc] initWithString:NSLocalizedString(string, nil)];
[scanner setCharactersToBeSkipped:nil];
NSString *output;
while (![scanner isAtEnd]) {
output = NULL;
// Find ${variable} templates
if ([scanner scanUpToString:@"${" intoString:&output]) {
[result appendString:output];
// Skip syntax
[scanner scanString:@"${" intoString:NULL];
output = NULL;
if ([scanner scanUpToString:@"}" intoString:&output]) {
id variable = nil;
// Check for the variable
if ((variable = [variables objectForKey:output])) {
if ([variable isKindOfClass:[NSString class]]) {
// NSString, append
[result appendString:variable];
} else if ([variable respondsToSelector:@selector(description)]) {
// Not a NSString, but can handle description, append
[result appendString:[variable description]];
}
} else {
// Not found, localize the template key and append
[result appendString:NSLocalizedString(output, nil)];
}
// Skip syntax
[scanner scanString:@"}" intoString:NULL];
}
}
}
[scanner release];
return result;
}
使用如下所示的localize文件:
"born message" = "I was born in ${birthYear} on a ${birthWeekDay}. ${byebye}";
"byebye" = "Cheers!";
我们可以完成以下结果......
NSDictionary *variables = [NSDictionary dictionaryWithObjectsAndKeys:[NSNumber numberWithInt:1986], @"birthYear", @"monday", @"birthWeekDay", nil];
NSString *finalString [self localizedStringFromTemplateString:@"born message" variables:variables];
NSLog(@"%@", finalString); // "I was born in 1986 on a monday. Cheers!"
如您所见,我还添加了一些额外的功能。 首先,任何未找到的变量(在我的示例中${byebye}
)都将被本地化并附加到结果中。 我这样做是因为我从我的应用程序包中加载了HTML文件并通过localize方法运行它们(当这样做时,我不会在创建扫描程序时本地化输入字符串)。 此外,我添加了除了NSString
对象之外的其他功能,以获得一些额外的灵活性。
这段代码可能不是性能最好或最漂亮的代码,但它可以在没有任何明显性能影响的情况下完成工作:)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.