编码又闹出了小问题
来源:互联网 发布:钟南山 知乎 编辑:程序博客网 时间:2024/04/27 15:47
编码总是让我感到烦恼,这次又有点小麻烦~~
import java.io.File;import java.util.Scanner;public class ScannerFileTest{ public static void main(String[] args) throws Exception{ //将一个File对象作为Scanner的构造器参数,Scanner读取文件内容 Scanner sc = new Scanner(new File("ScannerFileTest.java")); System.out.println("ScannerFileTest.java文件内容如下:"); while(sc.hasNextLine()){ //输出文件中的下一行 System.out.println(sc.nextLine()); } }}
经上次的教训,之后在编译时,我总这么敲命令:javac -d . -encoding utf-8 *.java
编译通过让我觉得在正常不过了,但之后运行给我带来的惊喜不是一点点
文件的内容蒸发了?
其实在敲这个之前,我根据题目信息自己写了个。而问题就在这,我的代码正常编译,运行结果也如我所料输出了文件内容。为什么这个基本一致的代码却存在问题?对比一下,大的出入就在注释,我一句都没写(个人没什么习惯写注释)。于是我把这个上面的注释加到我原来自己写的代码上,问题就来了。我尝试把中文去掉改成一些胡乱的字母串才发现,又是编码的问题……
上次同样是编码问题,说过使用ANSI编码能在不使用-encoding参数情况下通过编译,于是我把Notepad++编码改为ANSI。编译后运行,果然没问题。
要么以后就用ANSI编码算了,虽然网上多数推荐UTF-8,但也不知道为什么要这样做。有了这样的想法后,还是看了几篇关于ANSI,UTF-8,Unicode等的资料。再回来看代码,突然地,想起这几个IO类好像曾经见过在构造函数参数列里写有字符编码的参数。
于是抱着好奇心在原代码上做了些小改动:
Scanner sc = new Scanner(new File("ScannerFileTest.java") , "UTF-8");
再按照老套路编译运行,得出我想要的结果了。
搞笑,去看了下API文档,Scanner果真有这么一个构造器
Scanner
public Scanner(InputStream source,
String charsetName)构造一个新的 Scanner,它生成的值是从指定的输入流扫描的。来自该流的字节通过指定字符集转换成字符。
参数:
source - 要扫描的输入流
charsetName - 用于将来自该流的字节转换成要扫描的字符的编码类型
抛出:
IllegalArgumentException - 如果指定字符集不存在
之后又瞥了一眼原先使用的构造器
Scanner
public Scanner(InputStream source)构造一个新的 Scanner,它生成的值是从指定的输入流扫描的。取自该流的字节通过底层平台的默认字符集转换成字符。
参数:
source - 要扫描的输入流
我好奇默认字符集,点开查看
defaultCharset
public static Charset defaultCharset()
返回此 Java 虚拟机的默认 charset。
默认 charset 在虚拟机启动时决定,通常根据语言环境和底层操作系统的 charset 来确定。
返回:
默认 charset 的 charset 对象
从以下版本开始:
1.5
这是一个java.nio.charset.Charset类的静态方法,我将原来的代码又稍作修改添加了:
System.out.println(Charset.defaultCharset());
运行后发现,原来一直以来,我都用着这该死的GBK
那如果ANSI编码没有产生问题,那这GBK跟ANSI究竟有什么关系?兼容?
我查了下,有个总结很简单易懂,引用过来
所谓的「ANSI」指的是对应当前系统 locale 的遗留(legacy)编码。[1]
所谓的「Unicode」指的是带有 BOM 的小端序 UTF-16。[2]
所谓的「UTF-8」指的是带 BOM 的 UTF-8。[3]
[1] Windows 里说的「ANSI」其实是 Windows code pages,这个模式根据当前 locale 选定具体的编码,比如简中 locale 下是 GBK。把自己这些 code page 称作「ANSI」是 Windows 的臭毛病。在 ASCII 范围内它们应该是和 ASCII 一致的。
[2] 把带有 BOM 的小端序 UTF-16 称作「Unicode」也是 Windows 的臭毛病。Windows 从 Windows 2000 开始就已经支持 surrogate pair 了,所以已经是 UTF-16 了,「UCS-2」这个说法已经不合适了。UCS-2 只能编码 BMP 范围内的字符,从 1996 年起就在 Unicode/ISO 标准中被 UTF-16 取代了(UTF-16 通过蛋疼的 surrogate pair 来编码超出 BMP 的字符)。都十多年了,求求大家别再误称了……
[3] 把带 BOM 的 UTF-8 称作「UTF-8」又是 Windows 的臭毛病。如果忽略 BOM,那么在 ASCII 范围内与 ASCII 一致。另请参见:「带 BOM 的 UTF-8」和「无 BOM 的 UTF-8」有什么区别?
作者:梁海
链接:https://www.zhihu.com/question/20650946/answer/15745831
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
这么说ANSI编码在我的机子里就是GBK,那一切都说的通了~~
后来我又注意到一个细节
我右击鼠标新建一个文本文档,使用Notepad++打开后,它是ANSI编码的
而我在Notepad++,这个不知道叫做什么栏
的“文件-新建”,它是UTF-8编码
于是今天解决了这个编码问题,还完成了另外两个上次遗留的问题:
①两个不同的创建文件方式有什么区别?
②ANSI编码可以通过编译,UTF-8不能通过,为什么?
编码&注释的小问题(未完成)
总结:我机子的操作系统默认GBK
- 编码又闹出了小问题
- 又闹了一次
- 下午闹了个小笑话...
- 又出BUG了
- proteus仿真出了点小问题
- android,新手出了点小问题
- 小闹局域网
- 编码问题,又来?!
- 闹够了没有
- 今天做android应用出了点小问题
- 城管“又”打死人了,韩国“又”出研究了
- 我们的销售出了什么问题?--又谈销售管理
- 梨花姐姐又出新诗了!!!
- 问题又出现了
- 小歪又挂了...
- ADO出了问题
- 又是编码的问题
- 又是编码问题,hibernate
- 资源
- 笔试题11. 你是对称二叉树吗?
- hdu2594 Simpsons’ Hidden Talents (kmp)
- C++实践参考:IP地址类
- 完美主义容易导致效率低下
- 编码又闹出了小问题
- EL表达式字符串的加法
- Android WebView常见问题及解决方案汇总
- 活动选择
- 算法导论—Trie树
- 强连通分量分解
- 腾讯-基础研究-实习岗 笔试
- javascript函数的几点总结
- nginx运行时报错:error while loading shared libraries: libpcre.so.3