node os模块读取hostname乱码

  • 问题原因:
  • 解决方式
  • 附录:
    • 乱码
    • 计算机编码
    • 1.ASCII
    • 2.Latin1,ISO-8859-1
    • 3.GB2312,GBK,GB18030
    • 4.unicode,ucs2
    • 5.utf-8,utf-16

问题原因:

在读取hostname的过程中涉及到了GB2312 -> utf8 -> GBK 的过程,UTF-8 是 Unicode 的实现方式之一,UTF-8编码方式需要对unicode字符进行编码,部分字符unicode无法表示,unicode使用占位符来表示 U+FFFD ,U+FFFD的UTF-8编码出来,恰好是 ‘\xef\xbf\xbd’ 然后放到GBK/CP936/GB2312/GB18030的环境中显示的话,一个汉字2个字节,
最终的结果就是:锟斤拷——锟(0xEFBF),斤(0xBDEF),拷(0xBFBD)。

解决方式

解决方式为,避免使用utf8进行转换

const hostnameProcess = spawn('cmd',['/c', 'hostname']);
hostnameProcess.stdout.on('data',(data) => {const buf = iconv.encode(data, 'GKB');const hostname = iconv.encode(buf,'UTF-8').toString().trim();
})
exec(`hostname`,{ encoding: 'binary' },(err, stdout, stderr)=>{const buf =iconv.decode(stdout, 'cp936');const hostname = iconv.encode(buf,'UTF-8').toString().trim();
})

附录:

乱码

锟斤拷乱码:

源于GBK字符集和Unicode字符集之间的转换问题。Unicode和老编码体系的转化过程中,肯定有一些字,用Unicode是没法表示的,Unicode官方用了一个占位符来表示这些文字,这就是:U+FFFD REPLACEMENT CHARACTER。那么U+FFFD的UTF-8编码出来,恰好是 ‘\xef\xbf\xbd’。如果这个’\xef\xbf\xbd’,重复多次,例如 ‘\xef\xbf\xbd\xef\xbf\xbd’,然后放到GBK/CP936/GB2312/GB18030的环境中显示的话,一个汉字2个字节,最终的结果就是:锟斤拷——锟(0xEFBF),斤(0xBDEF),拷(0xBFBD)。

烫烫烫,屯屯屯乱码:

在windows平台下,ms的编译器(也就是vc带的那个)在 Debug 模式下,会把未初始化的栈内存全部填成 0xcc,用字符串来看就是"烫烫烫烫烫烫烫",

未初始化的堆内存全部填成0xcd,字符串看就是“屯屯屯屯屯屯屯屯”。

计算机编码

1.ASCII

刚开始计算机只在美国用,计算机中的八位字节(00000000-11111111)一共可以组合出256(2的8次方)种不同的状态,把其中的编号从0开始的32种状态分别规定了特殊的用途,一但终端、打印机遇上约定好的这些字节被传过来时,就要做一些约定的动作。遇上00x10, 终端就换行,遇上0x07, 终端就向人们嘟嘟叫,例好遇上0x1b, 打印机就打印反白的字,或者终端就用彩色显示字母,这些0x20以下的字节状态称为控制码。

之后又把所有的空格、标点符号、数字、大小写字母分别用连续的字节状态表示,一直编到了第127号,这样计算机就可以用不同字节来存储英语的文字了,这个方案叫做 ANSI 的ASCII编码(American Standard Code for Information Interchange,美国信息互换标准代码)。当时世界上所有的计算机都用同样的ASCII方案来保存英文文字。

2.Latin1,ISO-8859-1

随着发展,计算机开始普及,当计算机流传到欧洲时,问题再次出现,原本的ASCII编码只能解决美国人的编码问题,无法将欧洲的文字表示出来。于是乎,欧洲人就把ASCII码中没用到的第一位给用了,即:

ASCII码用一个字节的后七位,表示范围是0-127;
欧洲人把这个字节的第一位也用了,表示范围0-255。除去原本的0-127,剩下128-255:128-159之间为控制字符,160-255位文字符号,其中包括了西欧语言、希腊语、泰语、阿拉伯语、希伯来语。砖家们决定把他们的编码名称叫做Latin1,后面由于欧洲统一制定ISO标准,所以又有了一个ISO的名称,即ISO-8859-1。

3.GB2312,GBK,GB18030

等中国人开始使用计算机时,已经没有可以利用的字节状态来表示汉字,况且有6000多个常用汉字需要保存。于是把那些127号之后的奇异符号们直接取消掉并规定:一个小于127的字符的意义与原来相同,但两个大于127的字符连在一起时,就表示一个汉字,前面的一个字节(高字节)从0xA1用到0xF7,后面一个字节(低字节)从0xA1到0xFE。这样就可以组合出大约7000多个简体汉字。在这些编码里,还把数学符号、罗马希腊的字母、日文的假名们都编进去了,连在 ASCII 里本来就有的数字、标点、字母都统统重新编了两个字节长的编码,这就是常说的全角字符,而原来在127号以下的那些就叫半角字符。这种汉字方案叫做 GB2312。GB2312 是对 ASCII 的中文扩展。

但是中国的汉字太多了,人们很快就发现有许多人的人名没有办法在这里打出来。于是不得不继续把 GB2312 没有用到的码位补上。后来还是不够用,于是干脆不再要求低字节一定是127号之后的内码,只要第一个字节是大于127就固定表示这是一个汉字的开始,不管后面跟的是不是扩展字符集里的内容,结果扩展之后的编码方案被称为 GBK 标准。GBK 包括了 GB2312 的所有内容,同时又增加了近20000个新的汉字(包括繁体字)和符号。

后来少数民族也要用电脑了,于是再扩展,又加了几千个新的少数民族的字,GBK 扩成了 GB18030

GB18030的编码采用单字节、双字节和4字节方案。其中单字节、双字节和GBK是完全兼容的。4字节编码的码位就是收录了CJK扩展A的6582个汉字。

GBK是国家标准GB2312基础上扩容后兼容GB2312的标准。GBK的文字编码是用双字节来表示的,即不论中、英文字符均使用双字节来表示,为了区分中文,将其最高位都设定成1。GBK包含全部中文字符,是国家编码,通用性比UTF8差,不过UTF8占用的数据库比GBK大。

GBK、GB2312等与UTF8之间都必须通过Unicode编码才能相互转换:
GBK、GB2312--Unicode--UTF8
UTF8--Unicode--GBK、GB2312

GB2312、GBK都属于双字节字符集 (DBCS)。

4.unicode,ucs2

各个国家都像中国这样搞出一套自己的编码标准,结果互相之间谁也不支持别人的编码

一个叫 ISO (International Organization for Standardization,国际标谁化组织)的国际组织决定着手解决这个问题。方法很简单:废除了所有的地区性编码方案,重新搞一个包括了地球上所有文化、所有字母和符号的编码,称之为 UCS(Universal Multiple-Octet Coded Character Set),俗称 UNICODE。

UNICODE 开始制订时,计算机的存储器容量极大地发展了,空间再也不成为问题了。于是 ISO 就直接规定必须用两个字节,也就是16位来统一表示所有的字符,对于ascii 里的那些“半角”字符,UNICODE 包持其原编码不变,只是将其长度由原来的8位扩展为16位,而其他文化和语言的字符则全部重新统一编码。由于"半角"英文符号只需要用到低8位,所以其高8位永远是0,因此这种大气的方案在保存英文文本时会多浪费一倍的空间。

UNICODE 是用两个字节来表示为一个字符,他总共可以组合出 65535 不同的字符,这大概已经可以覆盖世界上所有文化的符号。如果还不够也没有关系,ISO已经准备了UCS-4方案,说简单了就是四个字节来表示一个字符,这样我们就可以组合出21亿个不同的字符出来(最高位有其他用途)

5.utf-8,utf-16

UNICODE 来到时,一起到来的还有计算机网络的兴起,UNICODE 如何在网络上传输也是一个必须考虑的问题,于是面向传输的众多 UTF(UCS Transfer Format)标准出现了,顾名思义,UTF8 就是每次8个位传输数据,而UTF16就是每次16个位,只不过为了传输时的可靠性,从UNICODE到UTF时并不是直接的对应,而是要过一些算法和规则来转换。

在网络里传递信息时有一个很重要的问题,就是对于数据高低位的解读方式,一些计算机是采用低位先发送的方法,例如我们PC机采用的 INTEL 架构,而另一些是采用高位先发送的方式,在网络中交换数据时,为了核对双方对于高低位的认识是否是一致的,采用了一种很简便的方法,就是在文本流的开始时向对方发送一个标志符——如果之后的文本是高位在位,那就发送"FEFF",反之,则发送"FFFE"。可以用二进制方式打开一个UTF-X格式的文件,开头两个字节即是这两个字节

UNICODE 符号范围(十六进制) UTF-8编码方式(二进制)
0000 0000-0000 007F 0xxxxxxx
0000 0080-0000 07FF 110xxxxx 10xxxxxx
0000 0800-0000 FFFF 1110xxxx 10xxxxxx 10xxxxxx
0001 0000-0010 FFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx

总结:

1.为了处理英文字符,产生了ASCII码。

2.为了处理中文字符,产生了GB2312。

3.为了处理各国字符,产生了Unicode。

4.为了提高Unicode存储和传输性能,产生了UTF-8

node os模块读取hostname乱码相关推荐

  1. Node.js OS 模块

    Node.js 工具模块 Node.js os 模块提供了一些基本的系统操作函数.我们可以通过以下方式引入该模块: var os = require("os") 方法 序号 方法 ...

  2. AI算法工程师 | 02人工智能基础-Python基础(四)os模块_打开读取文件

    文章目录 Python基础语法 之 文件和流 os 模块 调用操作系统命令 操作文件和目录 案例-文件重命名 打开读取文件 打开文件 读取文件 补充-中文编码问题 Python基础语法 之 文件和流 ...

  3. python中文件的读取与写入以及os模块

    1.文件读取的三部曲:打开 ---> 操作 ----> 关闭 r(默认参数): -只能读,不能写 -读取文件不存在 会报错 FileNotFoundError: [Errno 2] No ...

  4. python文件的读取与写入_python中文件的读取与写入以及os模块

    1.文件读取的三部曲:打开 ---> 操作 ----> 关闭 r(默认参数): -只能读,不能写 -读取文件不存在 会报错 FileNotFoundError: [Errno 2] No ...

  5. bufferedreader读取中文乱码_python之pandas模块关于csv文件乱码问题解决

    介绍 相信部分小伙伴们在处理windows系统生成的csv文件时会遇到中文显示乱码的问题,尤其是使用Excel打开这类文件时这类问题尤为突出. 解决 如图,我们通过Excel工具打开该csv文件时,中 ...

  6. 苹果系统python读取文件_python中文件的读取与写入以及os模块

    1.文件读取的三部曲:打开 ---> 操作 ----> 关闭 r(默认参数): -只能读,不能写 -读取文件不存在 会报错 FileNotFoundError: [Errno 2] No ...

  7. python读取文件夹下特定的文件_python os模块获取指定文件夹下所有文件名

    本文采用os.walk()和os.listdir()两种方法,获取指定文件夹下的文件名. python os模块获取指定文件夹下所有文件名 第一种方法使用os.walk(): os.walk() 方法 ...

  8. node中模块系统及核心模块、执行node文件

    node中模块系统: 1.模块系统:核心模块.第三方模块. 自己写的模块. 2.网页中所有的路径都是URL,而不是文件路径. 3.node偏底层开发,开启的服务器完全是一个黑盒子,所有的资源默认都是不 ...

  9. python笔记6 模块与包 程序开发规范 包 re sys time os模块

    模块与包 python 模块首引用加载到内存,如果再次引用此模块,直接从内存中读取. python文件分为:执行文件(解释器运行的文件),被引用文件(import) 模块引用一共发生了3件事: 1.他 ...

最新文章

  1. python中的中文乱码问题深入分析
  2. @RequestMapping的使用
  3. 英语笔记3(git)
  4. 有关单点登录的几种方案
  5. 月均数据_利用Python进行数据分析(附详细案例)
  6. filename: core/loader.php,使用第三方包后出现的这个错误,你们都遇到过吗?
  7. 基于hadoop架构的企业数字化转型,阿里数据中台实战案例
  8. 大数据分析项目成功的五项基本原则
  9. SpringMVC核心
  10. html代码 层次选择器,CSS样式类的实例代码(导航栏、分页、层级选择器)
  11. 计算机学院品牌活动总结,计算机学院研究生会工作总结
  12. python复数的模
  13. svg中marker元素的理解
  14. 建立“顾客购买图书”的活动图(使用泳道)
  15. 求一元多项式 P(x) = a0 + a1x + a2x^2 + ... + anx^n 的值P(x0)。
  16. FileZilla 下载
  17. 解决 VS Code 卡顿 卡死 电脑变卡 CPU 运行高
  18. java程序作弄别人_我的世界:作弄基友,戏耍熊孩子?家中常备红石陷阱,谁来谁遭殃!...
  19. 计算机中保存和另存为,电脑另存为在哪里
  20. ERP/MIS系统中集成命令行式的功能调用

热门文章

  1. Mybatis 踩坑报错-第一个mybatis程序
  2. 例说linux内核与应用数据通信(三):读写内核设备驱动文件
  3. 第19章、 认识与分析登录档
  4. 聊聊职场或个人事业的生存法则
  5. 日语二级语法汇总(part5/16)
  6. Ubuntu修改终端下的语言(中文或英文)
  7. hgame 2022 PWN 部分题目 Writeup
  8. 在OC项目中添加Swift文件并实现混合编程
  9. 现代应用参考架构之 OpenTelemetry 集成进展报告
  10. hive | 解决character '​' not supported here