写于:2014-06-20	最近一次更新:2015-08-23

Trouble:

Linux文件名乱码问题,文件内容乱码问题, 在Linux中打开windows下文件时乱码,批量处理乱码文件和乱码文件名

Oneway:

目前不能直接查看文件名的编码类型,但可以用convmv不加--notest参数的 命令convmv -f GBK2132 -t UTF-8 hello??.txt 查看打印的文件名是否正确, 确认正确后再加--notest参数正式执行转换; 用file -i hello你好.txt查看当前文件内容的编码类型; 文件名乱码用convmv命令转换;文件内容乱码用iconv命令转换; convmv与iconv中的参数-f 指出转换前的编码,参数-t 指定转换后的编码 单个处理文件乱码问题: 文件名乱码处理:convmv -f GBK -t UTF-8 --notest hello??.txt , 将hello你好.txt的文件名编码从GBK转换成UTF-8 文件内容乱码处理:iconv -f GBK -t UTF-8 hello1.txt -o hello2.txt , 将hello1.txt的内容以GBK编码读取并转换成UTF-8编码后输出为hello2.txt保存 批量处理多个文件乱码问题: 文件名乱码批量处理: convmv -f GBK -t UTF-8 --notest -r Test目录 , 将Test目录自身及其下的子目录和文件的名称全部从GBK转码为UTF-8 文件内容乱码批量处理: find Test/ -type f -exec iconv -sc -f GBK -t UTF-8 '{}' -o '{}' \; (这个命令会将Test目录下的所有是GBK编码的文件转换为UTF-8编码。 对find -exec来说,-exec必须由一个;结束,因为通常shell都会对;进行处理, 所以用\;防止这种情况,注意 \;前有一个空格,有空格\;才会作为参数被解析。 {}写做'{}',也是为了避免被shell过滤。)

Details:

如果只是需要正确显示文件内容以便现在查看,而不进行编码转换, 可以在/etc/vimrc或者~/.vimrc 文件中添加以下内容: set encoding=utf-8 fileencodings=ucs-bom,utf-8,cp936,gb18030,big5,latin1 这样,就可以让vim自动识别UTF-8或者GBK编码的文件, 就是依照fileencodings提供的编码列表尝试读取, 如果没有找到合适的编码,就用latin-1(ASCII)编码读取打开。 其中,ucs-bom 是一种非常严格的编码, 非该编码的文件几乎没有可能被误判为 ucs-bom,因此放在第一位。 utf-8 也相当严格,除了很短的文件外(例如许多人津津 乐道的 GBK 编码的“联通”被误判为 UTF-8 编码的经典错误), 现实生活中一般文件是几乎不可能被误判的,因此放在第二位。 接下来是 cp936 和 gb18030,这两种编码相对宽松,如果放前面的话, 会出现大量误判,所以就让它们靠后一些。 cp936 的编码空间比 gb18030 小,所以把 cp936 放在 gb18030 前面。 至于big5,它的严格程度和cp936差不多,但是很少编辑这些编码的文件, 因此把cp936 和 gb18030靠前放,以保证这些编码的识别。 最后就是 latin1 了,它是一种极其宽松的编码,以至于我们不得不把它放在最后一位。 不过可惜的是,当你碰到一个真的 latin1 编码的文件时,绝大部分情况下, 它没有机会 fall-back 到 latin1,往往在前面的编码中就被误判了。 不过,大部分人没有太多机会接触这样的文件。 (其实,可以在vim正常模式下使用:set fileencoding=utf-8直接对文件内容进行编码转换) vim字符相关知识: Vim 有四个跟字符编码方式有关的选项, encoding、fileencoding、fileencodings、termencoding (这些选项可能的取值请参考 Vim 在线帮助 :help encoding-names), 它们的意义如下: * encoding: Vim 内部使用的字符编码方式, 包括 Vim 的 buffer (缓冲区)、菜单文本、消息文本等。 默认是根据你的locale选择.用户手册上建议只在 .vimrc 中改变它的值, 事实上似乎也只有在.vimrc 中改变它的值才有意义。 你可以用另外一种编码来编辑和保存文件,如你的vim的encoding为utf-8, 所编辑的文件采用cp936编码,vim会自动将读入的文件转成utf-8(vim的能读懂的方式), 而当你写入文件时,又会自动转回成cp936(文件的保存编码). * fileencoding: Vim 中当前编辑的文件的字符编码方式, Vim 保存文件时也会将文件保存为这种字符编码方式 (不管是否新文件都如此)。 * fileencodings: Vim 自动探测fileencoding的顺序列表, 启动时会按照它所列出的字符编码方式逐一探测即将打开的文件的字符编码方式, 并且将 fileencoding 设置为最终探测到的字符编码方式。 因此最好将Unicode 编码方式放到这个列表的最前面, 将拉丁语系编码方式 latin1 放到最后面。 * termencoding: Vim 所工作的终端 (或者 Window 的 Console 窗口) 的字符编码方式。 如果vim所在的term与vim编码相同,则无需设置。如其不然, 你可以用vim的termencoding选项将自动转换成term的编码,在显示的时候, Vim 会把内部编码转换为屏幕编码,再用于输出。 内部编码中含有无法转换为屏幕编码的字符时,该字符会变成问号, 但不会影响对它的编辑操作。如果 termencoding 没有设置, 则直接使用encoding, 不进行转换。 举个例子,当你在 Windows 下通过 telnet 登录 Linux 工作站时, 由于 Windows 的 telnet 是 GBK 编码的,而 Linux 下使用 UTF-8 编码, 你在 telnet 下的 Vim 中就会乱码。 此时有两种消除乱码的方式: 一是把 Vim 的 encoding 改为 gbk ;使用该方法时, 如果遇到编辑的文件中含有 GBK 无法表示的字符时,这些字符就会丢失。 另一种方法是保持 encoding 为 utf-8,把 termencoding 改为 gbk, 让 Vim 在显示的时候转码。使用该方法时,虽然由于终端所限, 某些字符无法显示,但在编辑过程中这些字符是不会丢失的。 注意:对于Linux图形界面下的 GVim,它的显示不依赖 TERM, 因此 termencoding 对于它没有意义。在 GTK2 下的 GVim 中, termencoding 永远是 utf-8 ,并且不能修改。 而 Windows 下的 GVim 则忽略 termencoding 的存在。