我有一个我叫 poscar1.cif
的文件,我想在此文件中的特定行中插入变量的内容。
例如,Line 24
,当前读取:
_cell_length_a
我想处理我的变量a
的内容(在我的功能中定义为a=5.3827
),所以这样的行现在读取:
_cell_length_a 5.3827
有没有办法使用SED或尴尬做到这一点?我正在使用bash脚本来完成此操作(不幸的是,完整的脚本太大而无法发布)。
由于资深人士 ED 实用程序不再引起足够的关注:
a=5.3827
ed -s poscar1.cif <<EOF
g/^_cell_length_a$/ s//& $a/
w
EOF
ed
真正编辑文件在适当的位置,与 sed
不同的 -i
选项 [1] 。
sed
从ed
借了许多功能,因此功能有很大的重叠,但也存在重要差异,其中一些表面表面。
-
-s
抑制ed
的状态消息。 -
poscar1.cif
是要编辑的输入文件。 -
<<EOF ...
是此处包含ed
-ed
命令的文档,其命令要求其命令来自 stdin ,并且每个命令都在自己的行上。 -
g/^_cell_length_a$/
...是(基本)正则表达式(正则表达式),它匹配所有完全包含_cell_length_a
的行 -g
可确保如果完全没有匹配,则不会报告任何错误。- 请注意,
$
是-ESCCT,可保护它免受此处遗传中的 shell 的解释(在 this 实例中并不是必需的,但是很好的做法)。
- 请注意,
-
s//& $a/
...//
在匹配线上重复对最近使用的正则搜索,并用自身替换比赛(&
),然后是一个空间和变量$a
的值。- 请注意,由于此处的开放定界符(
EOF
)是 noceed , shell shell 可变扩展确实发生了;本质上,壳体像双引号的字符串一样对其进行处理。
- 请注意,由于此处的开放定界符(
-
w
将修改后的缓冲区写回输入文件。- 要调试,请使用
,p
代替w
,以便仅 print 未经其写回文件而无需。
- 要调试,请使用
[1] RE入境更新:
更准确地说, ed
保留了文件的现有 inode ,可确保保留所有文件的属性。
但是,它确实不是覆盖现有文件的单个字节,但是将整个 thother 文件读取到存储器中的一个缓冲区中,并写入整个缓冲区当被要求时到文件。
这使 ed
仅适用于小的文件,足以将整体读取到存储器中。
相比之下, sed -i
( gnu 和 bsd sed
),其 gnu 4.1 对应物, awk -i inplace
,以及 perl -i
替换 new>新创建一个一个,这意味着这意味着他们:
- 销毁Symlink(!) - 如果输入文件为a symlink ,它是替换为同名的常规文件
- 重要的情况很重要:说您的外壳初始化文件
~/.bashrc
是a symlink 对您在源控制下保留的文件的 symlink ;然后,您安装了使用sed -i
修改~/.bashrc
的工具,该工具将其替换为常规文件,并且链接到您的源控制版本。 - 更重要的是,BSD
sed
的行为甚至引入了安全风险(见下文)。
- 重要的情况很重要:说您的外壳初始化文件
- do 不是保留原始文件创建日期(在支持的情况下;例如,在OSX上)
他们 do ,但是,
- Preserve 扩展属性(在支持的情况下;例如,在OSX上)
保存文件权限
- 注意: BSD
sed
与 symlinks 介绍A 安全风险:- symlink 的权限被复制到替换文件,而不是symlink target 。由于symlinks get 可执行文件默认情况下,>您总是会以可执行文件 file file 最终结束,无论输入文件是否可执行。<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<</li>
- 幸运的是, gnu
sed
正确处理此情况。
- 注意: BSD
sed
, gawk
和 perl
可以通过采取额外的步骤来解决上述问题,但是只有在保留原始Inode时才可以确保一件事,就像ed
一样,可以确保strong>:
当文件被监视为更改的文件通过其Inode号码(例如,使用tail -f
),而不是保留监视的Inode中断。
您可以使用SED来做到这一点,具体取决于您对Dawg问题的回答
sed -i -e '24s/$/5.3827/' poscar1.cif
或者是模式
sed -i -e '/_cell_length_a/s/$/5.3827/' poscar1.cif
第一个使用给定的数字进入线路,以后将应用于与第一组斜线中模式匹配的任何行。无论哪种情况,它都将用最后两个斜线之间的值"替换"线的末端。
使用示例,您可以做类似的事情:
sed -i 's/(_cell_length_a)/1 5.3827/' poscar1.cif
在哪里,
-
-i
选项说要编辑到适当的文件,而不是创建副本 - 时髦的引用部分是一个字符串,指定正则表达式aka正则
-
poscar1.cif
是文件
很难阅读正则语法。查找和替换的基本格式是:
s/find/replace/
其中 find
是您要寻找的行的文本,而 replace
是替换该文本的文本。
如果我们想在替换中使用一部分查找字符串,则通过将其与(
和)
一起对其进行分组,然后使用1
在替换字符串中参考它。以下附加物替换为包括查找的任何行:
s/(find)/1replace/
请记住,如果您的字符串包含它们,则需要特别处理特殊的逃生字符或元字符。