用bash中的增量计数器替换两个字符串中包含的字符串

Posted

技术标签:

【中文标题】用bash中的增量计数器替换两个字符串中包含的字符串【英文标题】:replacing a string contained withing two strings with an incremental counter in bash 【发布时间】:2020-07-09 22:53:58 【问题描述】:

我正在尝试更改如下所示的文件:

>sample_A#Dakota
text
text
text
>text_2#Idao
text
text
text
>junk_1#Alabama
text
text
text
>example_4#Dakota
text
text
text
>example5#Honduras
text
text
text

到一个看起来像这样的文件:

>model_1#Dakota
text
text
text
>model_2#Idao
text
text
text
>model_3#Alabama
text
text
text
>model_4#Dakota
text
text
text
>model_5#Honduras
text
text
text

所以,我需要找到 > 和 # 之间的文本,并将其替换为“model”,后跟一个递增的数字。我找到了一些仅针对单独做这些事情的答案,但我无法将它们结合起来。我想使用 bash,使用 sed 或 awk 之类的单行答案。 我试过这个:

awk 'BEGIN  cntr = 0  />/,/#/  cntr++ ; print "model", cntr  !/>/,/#/  print $0 ' infile

但我得到了这个:

model 1
text
text
text
model 2
>text_2#Idao
text
text
text
model 3
>junk_1#Alabama
text
text
text
model 4
>example_4#Dakota
text
text
text
model 5
>example5#Honduras
text
text
text

提前致谢, T

【问题讨论】:

/regexp1/,/regexp2/ 语法用于定义与这些正则表达式匹配的行组,而不是用于单行匹配.. 应改为 />.*#/ 【参考方案1】:
$ awk '/^>.*#/sub(/^>[^#]+/, ">model_" ++c) 1' ip.txt
>model_1#Dakota
text
text
text
>model_2#Idao
text
text
text
>model_3#Alabama
text
text
text
>model_4#Dakota
text
text
text
>model_5#Honduras
text
text
text
/^>.*#/ 如果行以> 开头并且行中有# sub 功能有助于搜索和替换第一个匹配项 /^>[^#]+/ 匹配从> 开始直到# 字符之前的字符 ">model_" ++c 替换字符串 c 会在开始时为零(因为这是数字上下文),++c 会在递增后给出值,所以我们第一次得到1,下一次得到2 等等

【讨论】:

【参考方案2】:
$ awk 'sub(/^>[^#]+/,"")$0=">model1_" (++cnt) $0 1' file
>model1_1#Dakota
text
text
text
>model1_2#Idao
text
text
text
>model1_3#Alabama
text
text
text
>model1_4#Dakota
text
text
text
>model1_5#Honduras
text
text
text

【讨论】:

【参考方案3】:

您也可以尝试一下吗?

awk 'match($0,/>.*#/)print ">model_"++count"#" substr($0,RSTART+RLENGTH);next 1' Input_file

【讨论】:

【参考方案4】:
awk '/^>/$0=">model_" ++c "#" $31' FS='[>#]' file

我使用># 作为字段分隔符。

输出:

>model_1#达科他州 文本 文本 文本 >model_2#伊道 文本 文本 文本 >model_3#阿拉巴马州 文本 文本 文本 >model_4#达科他州 文本 文本 文本 >model_5#洪都拉斯 文本 文本 文本

【讨论】:

【参考方案5】:

这可能对你有用(GNU sed 和 shell):

sed -E '/^>.*#/x;s/.*/expr & + 1/e;x;G;s/^[^#]*(.*)\n(.*)/echo "model_\2\1"/e' file

对于以> 开头并包含# 的行,在保持空间 (HS) 中增加一个计数器,将 HS 附加到当前行并重新排列为所需的格式。

【讨论】:

以上是关于用bash中的增量计数器替换两个字符串中包含的字符串的主要内容,如果未能解决你的问题,请参考以下文章

用SQL怎么把一列所有字符串中包含的空格都删除呢

如何在分配的空间中存储以 ASCII 转换的计数器寄存器中包含的值

排除某些其他文件中包含的键字符串文件的所有行

如何处理版本列表中包含的字符串导致的错误,按StrictVersion排序?

如何正确处理Shell 函数传人参数中包含的特殊字符

用bash中的另一个字符串替换结束括号