sed - 使用包含空格

时间:2016-10-05 19:30:32

标签: bash sed

我刚刚回到学习bash。目前正在开展我的一个项目,当我使用sed时遇到了一个问题,我试过在网上寻求帮助,但没有任何乐趣。我怀疑我可能没有使用正确的术语,所以我无法找到我正在寻找的东西。无论如何。

因此,在我的脚本中,我尝试将date的输出分配给变量。这是我脚本中的一行。

origdate=$(date)

当我调用它时输出如下:

Wed Oct  5 19:40:45 BST 2016

然后我的脚本的一部分生成一个文件并向其写入信息,其中一部分我试图使用sed来查找行并替换它的一部分。这是我第一次玩sed,到目前为止我已经成功地使用了它。但是,当我尝试这个时,我会陷入困境:

sed -i '/origdate=empty/c\'$origdate'' $sd/pingcheck-email-$job.txt

当我运行脚本并且它到达此行时,这就是我得到的错误:

sed: can't read Oct: No such file or directory
sed: can't read 5: No such file or directory
sed: can't read 19:52:56: No such file or directory
sed: can't read BST: No such file or directory
sed: can't read 2016: No such file or directory

我怀疑它与日期(变量)中的空格有关,我的问题是:我该如何解决这个问题?我可以接受“忽略”吗?空间?或者我应该只使用cut来剪切日期的字段,并将其设置为变量并再次将相同的内容设置为另一个变量? 即使有人能够指出我正确的方向,这将是伟大的!

提前致谢!

3 个答案:

答案 0 :(得分:1)

双引号变量

sed -i '/origdate=empty/c\'"$origdate"'' $sd/pingcheck-email-$job.txt

或者整个脚本

sed -i "/origdate=empty/c\$origdate" $sd/pingcheck-email-$job.txt

答案 1 :(得分:1)

问题不在于sed,而在于你的命令如何按日期分割bash字。

在bash中,在命令行上执行分词,以便将文本分解为参数列表。为了说明,我将运行一个仅输出第一个参数的简单脚本。

bash -c 'echo $1' ignored_0 foo bar

bash -c 'echo $1' ignored_0视为命令(在您的情况下为sed)并将foo bar视为参数。在这种情况下,foo bar被分为两个参数,foo和bar。

要将foo bar作为第一个参数传递,您需要将文本放在单引号或双引号中。请参阅GNU manual on quoting

bash -c 'echo $1' ignored_0 'foo bar'
bash -c 'echo $1' ignored_0 "foo bar"

当变量在单引号内时,不会发生参数扩展。

var="foo bar"
bash -c 'echo $1' ignored_0 '$var'
bash -c 'echo $1' ignored_0 "$var"

注意:在命令`bash -c'echo $ 1'中,我不希望$ 1在作为参数传递给bash之前扩展,因为这是我想要执行的代码的一部分。

当变量在引号之外时会发生参数扩展,但在扩展参数后将应用分词。从Word拆分部分的bash手册页中:

  

shell扫描参数扩展命令的结果   替换和未发生的算术扩展   用于分词的双引号。

来自GNU bash manual on Word Splitting

  

shell扫描参数扩展命令的结果   替换和未发生的算术扩展   用于分词的双引号。

var="foo bar"
bash -c 'echo $1' ignored_0 $var

Quote Removal中Shell扩展的最后一步,其中不带引号的引号字符在传递给命令之前被删除。以下命令显示''“”对传递的参数没有影响。

bash -c 'echo $1' ignored_0 foo''""

的应用

在您的示例中,$ origdate之后的尾随''是无关紧要的。重要的部分是$ origdate没有被引用,因此分词适用于扩展变量。

当-e not 传递给sed命令时,sed希望表达式位于一个参数中,或来自bash的单词。运行命令时,表达式为/origdate=empty/c\Wed,其余日期将被视为要应用于表达式的文件。

简单的解决方法是在要防止分词的字符串周围放置双引号。我已经修改了命令,这样任何人都可以在没有系统文件的情况下运行这个例子。

在此示例中,必须对\进行转义,以使其不被视为$的转义字符。

echo "origdate=empty" | sed "/origdate=empty/c\\$origdate"

您还可以更改正在使用的引号类型,而不会影响分词。

echo "origdate=empty" | sed '/origdate=empty/c\'"$origdate"

答案 2 :(得分:0)

你需要通过双斜线逃脱 \ / \%