如何判断Java字符串中的文本是否包含UTF-8编码的字符

4

有没有其他方法可以知道javaString是否包含UTF-8编码的character-encoding,例如阿拉伯语单词。

我尝试了这段代码:但它准确吗?能否达到目的?

char c = 'أ';
int num = (int) c;

if(num> 128)
// then UTF-8 characters exists 

3
“> 128”不是特指UTF-8编码。它仅仅表示非ASCII字符。你想测试的是“非ASCII字符”吗? - Matt Ball
4
在Java中,UTF-8编码中没有“String”这样的东西。那里的字符串始终为UTF-16。 - Joey
http://jchardet.sourceforge.net/ 可能会有帮助。 - Jayan
@Joey 我知道我问过它是否包含UTF-8字符。 - confucius
1
如果涉及到 Nammari,答案显然是不行的。始终如此。 - Joey
3个回答

2
“假设 UTF-8 == 非 ASCII 字符集。你可以对字符串进行 ASCII 编码和解码,然后将结果与原始字符串进行比较。如果它们不相等,则存在非 ASCII 字符。但是,你自己的示例也可以使用(几乎可以,应该是 >= 128),因为以下证明了确实所有小于 128 的 char 均为 ASCII:‘为了兼容性,128 个 ASCII 和 256 个 ISO-8859-1(Latin 1)字符被分配了 Unicode/UCS 代码点,这些代码点与早期标准中它们的代码相同’。”

 

第一个平面(代码点U+0000到U+FFFF)包含最常用的字符,被称为基本多语言平面或BMP。UTF-16和UCS-2都将该范围内的有效代码点编码为单个16位代码单元,其数值等于相应的代码点。
(“UTF-16”和“ASCII”,维基百科)
而“char”是UTF-16 “代码单元”。
然而,从整个问题来看,你最好先阅读Unicode和字符集方面每个软件开发者绝对必须知道的绝对最低限度(没有借口!)

1
所有合法的UTF-16字符串都可以被编码为合法的UTF-8字符串而不会丢失信息。只要不生成有缺陷的CESU-8即可。 - tchrist
@tchrist 我知道,但是嗯,你想说什么? :P UTF-8对我的回答完全不相关(请参见第一行) - Bart van Heukelom
我的评论本应该发在另一个答案上,而不是你的上面;抱歉。 - tchrist

1

Java(内部)始终使用UTF-16编码String,而与其内容无关。http://docs.oracle.com/javase/6/docs/api/java/lang/String.html

您可以将其转换为任何支持的编码,包括ASCII和UTF-8,但可能会丢失在所选编码中无法显示的字符。

根据您检查的原因,您可以将字符串转换为ASCII并将其读回到Java String中,然后查看它们是否匹配。如果匹配,则ASCII足以存储您的字符串。这将是稍后阅读您源代码的读者最明显的检查。

您还可以将每个字符的Unicode代码点与128进行比较,如果它们都小于等于127,则该字符串与ASCII兼容,即肯定不包含阿拉伯语。要获取字符串中字符的Unicode代码点,请使用str.codePointAt(index)

如果您明确想要查找阿拉伯文本,您应该明确检查阿拉伯字符。否则,您可能会得到法语、德语或许多其他使用重音字符的语言的误报。幸运的是,Unicode联盟将每种语言关联到块中,因此检查可能归结为cp >= beginningOfUnicodeBlock && cp <= endOfUnicodeBlock

编辑,由tchrist提示:有java.lang.Character.UnicodeBlockjava.lang.Character.UnicodeScript。后者在Java 7中添加。两者都可以用于分类Unicode代码点。

int cp = str.codePointAt(index);
if (UnicodeScript.ARABIC.equals(UnicodeScript.of(cp)) {
    // arabic character found
}

你不能以那种方式使用 char 变量。Unicode 代码点是 int - tchrist
此外,您想要测试脚本而不是块。请参阅Java 7的CharacterPattern类,或者只需使用ICU UCharacter类,该类更适合这种工作。 - tchrist
我编辑了帖子,使用代码点而不是字符。测试脚本听起来不错,但根据用例,在块上进行测试可能已经足够了。我不知道 ICU,它显然会添加外部依赖。此外,我不知道 Java 7 的 Character.UnicodeScript 或在 1.2 中添加的 Character.UnicodeBlock - user1252434

-1

我不相信有一种百分之百准确的方法来确定。UTF-8和UTF-16可以带有可选的字节顺序标记,您可以检测到它们。不能保证它会在那里,但是许多工具都包括它们,特别是对于UTF-16,因为它更重要。

Apache Commons IO包括一个方便的BOMInputStream类,用于读取带BOM标记的流,非常简单易用:

BOMInputStream bomIn = new BOMInputStream(in);
if (bomIn.hasBOM()) {
    // has a UTF-8 BOM
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接