`
yongboy
  • 浏览: 106207 次
  • 来自: ...
博客专栏
E16f1064-1c93-305c-9ed5-2118b09bada4
Servlet 3.0 学...
浏览量:0
社区版块
存档分类

获取文件字符集(或文件编码) De 工具类

阅读更多

一直对获取文件编码感兴趣,直到找到 jchardet 这个好东西,才解决了我的困惑。

写了一个获取文件编码的工具类,贴在下面,方便自己,方便他人:

package org.mozilla.intl.chardet;

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;

/**
 * 借助JCharDet获取文件字符集
 * @author icer
 * PS:
 * JCharDet 是mozilla自动字符集探测算法代码的java移植,其官方主页为:
 *      http://jchardet.sourceforge.net/
 * @date	2008/11/13 
 */
public class FileCharsetDetector {

	private boolean found = false;

	/**
	 * 如果完全匹配某个字符集检测算法, 则该属性保存该字符集的名称. 否则(如二进制文件)其值就为默认值 null, 这时应当查询属性 
	 */
	private String encoding = null;

	public static void main(String[] argv) throws Exception {
		if (argv.length != 1 && argv.length != 2) {

			System.out
					.println("Usage: FileCharsetDetector <path> [<languageHint>]");

			System.out.println("");
			System.out.println("Where <path> is d:/demo.txt");
			System.out.println("For optional <languageHint>. Use following...");
			System.out.println("		1 => Japanese");
			System.out.println("		2 => Chinese");
			System.out.println("		3 => Simplified Chinese");
			System.out.println("		4 => Traditional Chinese");
			System.out.println("		5 => Korean");
			System.out.println("		6 => Dont know (default)");

			return;
		} else {
			String encoding = null;
			if (argv.length == 2) {
				encoding = new FileCharsetDetector().guestFileEncoding(argv[0],
						Integer.valueOf(argv[1]));
			} else {
				encoding = new FileCharsetDetector().guestFileEncoding(argv[0]);
			}
			System.out.println("文件编码:" + encoding);
		}
	}

	/**
	 * 传入一个文件(File)对象,检查文件编码
	 * 
	 * @param file
	 *            File对象实例
	 * @return 文件编码,若无,则返回null
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	public String guestFileEncoding(File file) throws FileNotFoundException,
			IOException {
		return geestFileEncoding(file, new nsDetector());
	}

	/**
	 * 获取文件的编码
	 * 
	 * @param file
	 *            File对象实例
	 * @param languageHint
	 *            语言提示区域代码 eg:1 : Japanese; 2 : Chinese; 3 : Simplified Chinese;
	 *            4 : Traditional Chinese; 5 : Korean; 6 : Dont know (default)
	 * @return 文件编码,eg:UTF-8,GBK,GB2312形式,若无,则返回null
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	public String guestFileEncoding(File file, int languageHint)
			throws FileNotFoundException, IOException {
		return geestFileEncoding(file, new nsDetector(languageHint));
	}

	/**
	 * 获取文件的编码
	 * 
	 * @param path
	 *            文件路径
	 * @return 文件编码,eg:UTF-8,GBK,GB2312形式,若无,则返回null
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	public String guestFileEncoding(String path) throws FileNotFoundException,
			IOException {
		return guestFileEncoding(new File(path));
	}

	/**
	 * 获取文件的编码
	 * 
	 * @param path
	 *            文件路径
	 * @param languageHint
	 *            语言提示区域代码 eg:1 : Japanese; 2 : Chinese; 3 : Simplified Chinese;
	 *            4 : Traditional Chinese; 5 : Korean; 6 : Dont know (default)
	 * @return
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	public String guestFileEncoding(String path, int languageHint)
			throws FileNotFoundException, IOException {
		return guestFileEncoding(new File(path), languageHint);
	}

	/**
	 * 获取文件的编码
	 * 
	 * @param file
	 * @param det
	 * @return
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	private String geestFileEncoding(File file, nsDetector det)
			throws FileNotFoundException, IOException {
		// Set an observer...
		// The Notify() will be called when a matching charset is found.
		det.Init(new nsICharsetDetectionObserver() {
			public void Notify(String charset) {
				found = true;
				encoding = charset;
			}
		});

		BufferedInputStream imp = new BufferedInputStream(new FileInputStream(
				file));

		byte[] buf = new byte[1024];
		int len;
		boolean done = false;
		boolean isAscii = true;

		while ((len = imp.read(buf, 0, buf.length)) != -1) {
			// Check if the stream is only ascii.
			if (isAscii)
				isAscii = det.isAscii(buf, len);

			// DoIt if non-ascii and not done yet.
			if (!isAscii && !done)
				done = det.DoIt(buf, len, false);
		}
		det.DataEnd();

		if (isAscii) {
			encoding = "ASCII";
			found = true;
		}

		if (!found) {
			String prob[] = det.getProbableCharsets();
			if (prob.length > 0) {
				// 在没有发现情况下,则取第一个可能的编码
				encoding = prob[0];
			} else {
				return null;
			}
		}
		return encoding;
	}
}

 

网上有一些使用文章,但是使用起来,发现还是有一些问题的,看着官方实例,就自己写了一个。使用起来,感觉不错。

附件为jchardet包。

 

分享到:
评论
1 楼 aarontao 2008-11-18  
基于统计来进行字符集探查的,所以并不是百分百准确,并且需要字符串样本足够长。

相关推荐

    Unicode转码工具

    6. **注意事项**: 转码过程中要特别注意字符集的识别,错误的编码识别可能导致乱码。同时,有些特殊字符在某些编码中可能无法直接对应,需要特别处理。 7. **实际操作**: 使用“Unicode转码工具”这个软件,用户只...

    20180702203200qhuats2yfjslc8gifxbg1ci4de33ywoc.zip

    标题中的"20180702203200qhuats2yfjslc8gifxbg1ci4de33ywoc.zip"看起来像是一个日期时间戳加上一串随机字符组成的文件名,这通常是用来唯一标识文件或记录创建时间的方式。在IT行业中,这种命名方式常见于日志文件、...

    Properties插件

    6. **编码与字符集**:由于.properties文件可能包含多种语言,所以插件通常支持设置文件的编码和字符集,确保非ASCII字符的正确显示和保存。 7. **自动加载和刷新**:在开发过程中,当.properties文件被修改后,...

    C#多国语言包

    - 为了确保字符串正确显示,应使用Unicode编码,如UTF-8,以支持多种语言的字符集。 通过以上步骤,你可以创建一个具备多国语言支持的C#应用程序。这不仅增强了用户体验,也使你的软件能够更好地适应全球市场。...

    使用springboot实现自定义logo的二维码输出

    先上效果图 ![在这里插入图片描述]...通过设置编码提示类型,包括字符集、错误纠正级别和边距等,确保二维码的可读性和容错性。 2. 计算 logo 在二维码中的合适大小

    精易模块[源码] V5.15

    1、修正“编码_ansi到usc2”当末尾出现10或13字符时出错的BUG,感谢易友【@rmcs】反馈。 2、改名“文件_搜索1”改为“文件_搜索_深度”并修正备注及深度问题,感谢易友【@小爬虫】反馈。 3、改善“时间_取现行时间戳...

    设计Java EE应用程序-- J2EE应用程序国际化和本地化.doc

    编码是字符集的二进制表示,如UTF-8编码用于将Unicode字符转换为字节序列。 **5. 日期、时间与货币格式** 在国际化的应用中,日期、时间和货币的格式因地区而异。`java.text.SimpleDateFormat`和`java.text....

    国际化-i18n

    6. **Unicode支持**:Java完全支持Unicode,确保了全球各种字符集的兼容性,这对于处理多语言文本至关重要。 7. **Filter和Servlet的国际化**:在Web应用中,`HttpServletRequest`和`HttpServletResponse`接口以及`...

    深入浅出Hibernate源码

    在安装完mysql之后,请使用客户端或者phpmyadmin建立一个名为forum的mysql数据库,其字符集必须为UTF-8(见下面关于中文的说明,在phpmyadmin中应该选择utf8_general_ci)。另外还需要建立名为forum的用户,密码也为...

    fr.eni.TP:Quelques TPs de la semaine 2“启动àJava”

    【标题】"fr.eni.TP:Quelques TPs de la semaine 2“启动àJava”" 提供了一个关于Java编程的练习集,重点可能是针对第二周的学习内容,涉及如何启动和运行Java程序。这可能包括了基础的Java编程概念、环境配置以及...

    Scraps:Pequenos projetos feitos durante os estudos de javascript

    通过研究这些项目,初学者可以深入了解JavaScript的实际应用,而经验丰富的开发者则可以从中获取灵感,或检查不同的编码风格和最佳实践。同时,由于这些项目是学习过程中的产物,它们通常会以简洁明了的方式展示特定...

    PHP基础教程 是一个比较有价值的PHP新手教程!

    字符串可以由单引号或双引号引出的字段定义。注意不同的是被单引号引出的字符串是以字面定义的,而双引号引出的字符串可以被扩展。反斜杠(&#92;)可以被用来分割某些特殊字符。举例如下: $first = 'Hello'; $...

    论我国的EDI标准体系.pdf

    GB/T14805《用于行政、商业和运输业电子数据交换的应用级语法规则》,规定了字符集、语法级和数据组织规则;GB/T16703《用于行政、商业和运输业电子数据交换的语法实施指南》,提供了实施GB/T14805的指导;GB/T15947...

    深入浅出Hibernate

    是一个值得推荐的工具:http://www.mysqlfront.de/download.html&lt;br/&gt;&lt;br/&gt; 在安装完mysql之后,请使用客户端或者phpmyadmin建立一个名为forum的mysql数据库,其字符集必须为UTF-8(见下面关于中文的说明,在...

    利斯塔德塔里法斯

    TypeScript是JavaScript的一个超集,它提供了强类型、类、接口和其他高级特性,旨在提高大型代码库的可维护性和可读性。在前端开发中,使用TypeScript可以捕捉更多的类型错误,从而在编码阶段就能发现并修复问题,而...

    php_alura_primeiros_passos:一个Web上PHP格式,可在php上运行,并在其中包含以下内容。 丹麦语言发展和合作基金会(Vocêvai aprender desde os a Fundamentos da linguagem junto com)的名称为Boapráticaseo essencial conhecimento de uma boa modelagem Orientada a Objetos

    3. **文件操作**:学习读取、写入和操作本地文件系统,这对于存储和检索用户数据或生成动态内容至关重要。 4. **HTTP与Web交互**:了解HTTP协议的基本概念,如何使用PHP发送和接收HTTP请求,以及处理表单数据和...

Global site tag (gtag.js) - Google Analytics