我的Android应用程序检索SHOUTcast元数据并显示它。我有和非英文字符集问题。基本上,元数据显示为乱码。我将如何执行字符编码检测并正确显示文本?对不起,如果这是一个不平凡的问题,我不太熟悉这个话题。Android中的字符集检测
有问题的数据流是:http://skully.hopto.org:8000
我的Android应用程序检索SHOUTcast元数据并显示它。我有和非英文字符集问题。基本上,元数据显示为乱码。我将如何执行字符编码检测并正确显示文本?对不起,如果这是一个不平凡的问题,我不太熟悉这个话题。Android中的字符集检测
有问题的数据流是:http://skully.hopto.org:8000
由于vorrtex在他的评论中指出的上述情况,如果您的数据来源,以及形成的HTML代码,你可以从<meta content="...">
标签知道它的编码,这是最好的情况。您可以将此转换到Android(或其他Java实现)字符串代码,如:
// assume you have your input data as byte array buf, and encoding
// something like "windows-1252", "UTF-8" or whatever
String str = new String(buf, encoding);
// now your string will display correctly
如果你不知道的编码 - 你收到你的数据在未知格式的原始文本 - 你仍然可以尝试算法猜测它,使用统计语言模型。我刚刚找到了ICU - 国际组件为IBM项目,自由开放源码许可(商业用途OK),在http://site.icu-project.org/
它们提供Java和C++库。我刚刚添加了他们的Java JAR版本。 51.2到我的Android项目,它的工作就像一个魅力。我以前从文本文件中识别字符编码的代码是:
public static String readFileAsStringGuessEncoding(String filePath)
{
String s = null;
try {
File file = new File(filePath);
byte [] fileData = new byte[(int)file.length()];
DataInputStream dis = new DataInputStream(new FileInputStream(file));
dis.readFully(fileData);
dis.close();
CharsetMatch match = new CharsetDetector().setText(fileData).detect();
if (match != null) try {
Lt.d("For file: " + filePath + " guessed enc: " + match.getName() + " conf: " + match.getConfidence());
s = new String(fileData, match.getName());
} catch (UnsupportedEncodingException ue) {
s = null;
}
if (s == null)
s = new String(fileData);
} catch (Exception e) {
Lt.e("Exception in readFileAsStringGuessEncoding(): " + e);
e.printStackTrace();
}
return s;
}
Lt.d和Lt.e以上只是我对Log.d(TAG快捷键,“嗒嗒......” )。在我能想到的所有测试文件上工作得很好。我只关心APK文件的大小 - icu4j-51_2.jar的长度超过了9 MB,在添加之前我的整个包只有2.5 MB。但是很容易将CharsetDetector和它的依赖关系隔离开来,所以我最终添加了不超过50kB的内存。我需要复制到从ICU来源我的项目的Java类都在核心/ src目录/ COM/IBM/ICU /文本目录,分别为:
CharsetDetector
CharsetMatch
CharsetRecog_2022
CharsetRecog_mbcs
CharsetRecog_sbcs
CharsetRecog_Unicode
CharsetRecog_UTF8
CharsetRecognizer
此外,在CharsetRecog_sbcs.java有一个保护“ArabicShaping如;'成员,它想要拉更多的课程,但事实证明,对于字符集识别它不是必需的,所以我评论了它。就这样。希望能帮助到你。
Greg
但我必须使用输入流才能从元标记获取该值。同时,我应该将尚未知道的编码值传递给inputstreamreader。然后由于编码错误,字节信息完全丢失。即使我以后可以从meta标签中获得正确的编码,我该如何将其转换回正确的编码? – 2015-11-26 02:47:11
上面讨论的使用ICU库的方法在字节数组上工作,并且不需要先转换为字符串。或者有创意,例如将字节数组视为ASCII字符串来搜索标签,因为它们都是ASCII字符。我实际上这样做,但在JNI C++代码。 – gregko 2015-11-27 13:27:02
感谢关于ICU库的漂亮小贴士。似乎ArabicShaping成员在他们的Java库的最新版本中不再产生任何问题。 BTW:指出ICU库中的一个子集将包含在Android N中。 – moster67 2016-04-03 21:57:15
这取决于数据的来源。对于你的链接,你可以打开页面的HTML代码,你会看到''。这意味着编码是Windows-1252,如果您仅使用此站点,则可以对此编码名称进行硬编码并始终使用它。 – vorrtex 2013-03-16 09:56:21