linux - bash 中的字符串连接导致替换

标签 linux windows bash macos string-concatenation

我需要将一个文件读入一个数组,并在每一行的末尾连接一个字符串。这是我的 bash 脚本:

#!/bin/bash

IFS=$'\n' read -d '' -r -a lines < ./file.list
for i in "${lines[@]}"
do
    tmp="$i"
    tmp="${tmp}stuff"
    echo "$tmp"
done

但是,当我这样做时,会发生 replace 操作,而不是连接。

例如,在file.list中,我们有:

http://www.example1.com
http://www.example2.com

我需要的是:

http://www.example1.comstuff
http://www.example2.comstuff

但是在执行上面的脚本之后,我在终端上得到如下信息:

stuff//www.example1.com
stuff//www.example2.com

顺便说一句,我的电脑是 Mac 操作系统。

通过 awkprintfecho 命令连接字符串时也会出现此问题。例如 echo $tmp"stuff"echo "${tmp}""stuff"

最佳答案

文件 ./file.lst 很可能是在 Windows 系统上生成的,或者至少是使用 Windows 行尾约定保存的。

Windows 使用两个字符的序列来标记文本文件中行的结尾。这些字符是 CR (\r) 后跟 LF (\n)。类 Unix 系统(从版本 10 开始的 Linux 和 macOS)使用 LF 作为行尾字符。

代码中 read 前面的赋值 IFS=$'\n' 告诉 read 使用 LF 作为行分隔符。 read 不会将 LF 字符存储在它生成的数组 (lines[]) 中,而是从 lines[]CR 字符结尾。

tmp="${tmp}stuff" 行做了它应该做的事情,即将单词 stuff 附加到变量 的内容>tmp(从文件中读取的一行)。

从输入文件中读取的第一行包含字符串 http://www.example1.com,后跟 CR 字符。追加字符串stuff后,变量tmp的内容为:

http://www.example1.com$'\r'stuff

CR 字符不可打印。它在终端上打印时有一个特殊的解释:它在行的开头(第 1 列)发送光标而不更改行。

echo 打印上面的行时,它会打印(从新行开始)http://www.example1.com,然后是 CR 字符,将光标发送回打印字符串 stuff 的行首。 stuff 片段覆盖了该行 (http:) 上已打印的前 5 个字符,结果在屏幕上显示为:

stuff//www.example1.com

解决方案是从输入文件中删除 CR 字符。有多种方法可以实现这一目标。

从输入文件中删除 CR 字符的简单方法是使用以下命令:

sed -i.bak s/$'\r'//g file.list

它从文件 file.list 的内容中删除所有 CR 字符,将更新后的字符串保存回 file.list 文件并将原始 file.list 文件存储为 file.list.bak(一个备份副本,以防它没有产生您期望的输出)。

另一种删除 CR 字符的方法是要求 shell 在附加 stuff 的命令中删除它:

tmp="${tmp/$'\r'/}stuff"

当一个变量在像${tmp/a/b}这样的构造中扩展时,a$tmp中的所有出现替换为 b。在这种情况下,我们将 \r 替换为空。

关于linux - bash 中的字符串连接导致替换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43963118/

相关文章:

适用于 XP 的 Windows 防火墙规则

bash - xargs -0 后如何执行多个命令?

linux - 命令行 "cat >> "行为

linux - 在脚本中用 ext4 分区填充磁盘

linux - 在 linux 内核空间中将 char[] 转换为 __be16 类型

Java 打印 : Windows vs Linux

linux - fopen() 在/dev/ttyACM0 上失败

windows - 如何使用特定的图形驱动程序创建 OpenGL 上下文?

linux - 解析bash中两个字符串之间的值

bash - `printf "2+2 "| bc` 返回语法错误,`echo "2+2 "| bc` 有效,它们如何以不同的方式处理字符串?