TL; DR :在Java中,将通过charAt
方法从字符串获取的字符转换为字节总是产生相同的值?
我正在阅读用任意(我们未知)字符编码编码的文件。我需要解析这些文件并查找某些单词,例如“标签”。我对文件内容设置了一些限制,例如“在查找标签时,”TAG“的字节必须与它们的ASCII表示相同”。
例如,假设我有以下文件:
0x00 0x11 0x22 0x33 0x54 0x41 0x47 0x77 0x88 0x99 0xaa 0xbb
由于T,A和G的ASCII值分别为0x54
,0x41
和0x47
,我可以通过解析字节本身在文件中找到“TAG”。
0x00 0x11 0x22 0x33
的 0x54 0x41 0x47
0x77 0x88 0x99 0xaa 0xbb
但是,我需要硬编码我要查找的字节的值。为此,我调用String
的{{1}}方法并将char转换为一个字节
例如,我将如何验证“T”字节表示的任意字节(称为charAt(int i)
):
b
String tag = "TAG";
char t = tag.charAt(0);
if ((byte)t == b){
//magic goes here, such as comparing the 'A' and the 'G'
注意:代码实际上并非如此,验证算法更加优雅。
这在我的本地机器上工作正常。但是,这将在可能包含非常奇怪的编码的机器上运行。令我担心的是,将}
获得的字符转换为字节是否会产生不同的值,具体取决于计算机。我知道Java总是使用UTF-16字符编码对charAt
进行编码,但我担心从String转换为字符然后转换为字节可能会产生奇怪的结果。
那么,简而言之,将通过char
方法从String获取的字符转换为字节总是产生相同的值?或者它取决于外部因素?
谢谢你的帮助!
注意:我不能对字节本身进行硬编码(例如,在字节数组中),因为它们可能非常长并且将来可能会经常更改。
答案 0 :(得分:3)
java.lang.string.charAt
将始终返回一个16位UTF-16字符,当你将其转换为一个字节时,它总是相同的,尽管因为char
是一个16位无符号数据类型,所以它作为8位签名byte
可能会给您带来不必要的行为。但是,如果您的源数据是ASCII,您将获得您期望的行为类型。
答案 1 :(得分:2)
是charAt (int)
返回Java定义的char类型(UTF-16),因此始终与byte
相同。
相反,String.getBytes()
根据指定的字符集或操作系统的默认字符集(如果未指定)返回字节。
答案 2 :(得分:0)
使用(byte)
将字符转换为字节将在所有系统上提供相同的结果。
但是,您需要混合使用char
和byte
。你应该真的使用其中一个。混合这些概念会导致你怀疑的混乱。
答案 3 :(得分:0)
您可以使用Character.codePointAt(char c)
方法,而不是直接对它们进行类型转换。这应该保证每次都有相同的结果。