当前位置:主页 > 脚本语言 > Shell >

详解Shell脚本中^M的问题和解决方案

时间:2022-11-21 08:27:14 | 栏目:Shell | 点击:

在开发过程中,有时候不小心将Windows本地创建的shell脚本(以 .sh 结尾的脚本),传到linux系统中,通过 vi或者view命令查看文件时,发现在末尾发现出现了很多^M字符。

^M 是什么?

这个字符就是换行符。是由于跨平台解析的原因。
因为window和Linux下对行尾的换行的定义不同
Windows: \r\n
Linux/Unix: \n
Mac: \r

例子

出现的原因:
在DOS/Windows里,文本文件的换行符为\r\n,而在nix系统里则为\n,所以DOS/Windows里编辑过的文本文件到了nix里,每一行都多了个^M

导致的问题:
脚本可能无法正常执行,影响程序正常使用

临时解决方案1:

如果需要从表面上修改,只需使用替换命令就能将该字符给取消;#:%s/^M//g

临时解决方案2:

在linux上创建一个文件,名称为 xxx.sh,将这个问价下载到本地,然后将脚本内容粘贴进去,重新上传到linux上打开查看。

补:解决方法

 如果需要转换,我们只需要转换文件格式即可。你可以选择直接在服务器上调整。包括如下三种方式。
(1)使用linux命令dos2unix filename,直接把文件转换为unix格式
(2)使用sed命令sed -i "s/\r//" filename  或者 sed -i "s/^M//" filename直接替换结尾符为unix格式
(3)vi filename打开文件,执行 : set ff=unix 设置文件为unix,然后执行:wq,保存成unix格式。

本质原因

跨平台造成的编码格式问题。其实这个是历史遗留问题,根本原因就是对换行符的内存组成问题。在unix操作系统下的换行符格式为0A(ascii码),而dos格式下的换行符为 0D 0A(也就是),其实就显示为^M了。并且对于这个原因,也是有历史的。
unix将换行符的字符形式给转变了,然而,dos命令下任然保留着传统的表达方式;所以以后在进行跨平台开发的时候,前提就是考虑是否兼容,是否编码格式兼容这些基本的前提条件。

历史来源:
早期的计算机输出设备不是显示器,而是电传打字机,结构与普通的打字机差不多。有一个打印头在纸上打字,同时有一个电动机控制纸张的进出。当打印头到达行尾的时候,需要两个动作才能够到达下一行的行首:首先执行回车动作,将打印头移动到本行的行首,然后进行换行动作,电动机将纸张向上移动一行,这样打印头就处于下一行的行首,可以继续进行打印。回车和换行对应的控制字符分别是\r和\n,这就是windows中换行符为\r\n的由来。后来由于经常连续执行,所以在打印机中将这两个控制字符简化为一个控制字符,这就是Linux/Unix中的换行符\n的由来。

常用工具

dos2unix 将window下文本文件转成符合Linux系统要求的文件
unix2dos  与上面的命令的作用相反

您可能感兴趣的文章:

相关文章