Shell脚本,使用sed替换字符

Shell脚本,使用sed替换字符,shell,sed,Shell,Sed,在shell脚本中,我想使用sed将1bc1034gf45dna22(总共16个字符)替换为1b:c1:03:4g:f4:5d:na:22(用冒号分隔) 编辑 我试过了 sed 's/\w{2}/\w{2}:/g' a.txt > b.txt 其中a.txt具有 1bc1034gf45dna22 为什么不sed的/1bc1034gf45dna22/1b:c1:03:4g:f4:5d:na:2/g'文件?在任何GNU/Linux发行版上使用GNU/sed,您都可以使用扩展正则表达式。这将

在shell脚本中,我想使用sed将
1bc1034gf45dna22
(总共16个字符)替换为
1b:c1:03:4g:f4:5d:na:22
(用冒号分隔)

编辑

我试过了

sed 's/\w{2}/\w{2}:/g' a.txt > b.txt
其中
a.txt
具有

1bc1034gf45dna22

为什么不
sed的/1bc1034gf45dna22/1b:c1:03:4g:f4:5d:na:2/g'文件

在任何GNU/Linux发行版上使用GNU/sed,您都可以使用扩展正则表达式。这将把任意长度的字符串转换为每两个字母用冒号分隔的字符串:

echo 1bc1034gf45dna22 | sed -re 's/(\w{2})/\1:/g' -e 's/:$//'
在AIX平台上,您可以利用awk:

echo 1bc1034gf45dna22 | awk '
  BEGIN { FS=""; ORS=""; } 
  {
    for (i=1; i <=NF; i++) {
      if (i > 1 && (i + 1) % 2 == 0) { 
        print(":"); 
      }  

      print($i);
    }
  }'
echo 1bc1034gf45dna22 | awk'
开始{FS=”“;ORS=”“;}
{
对于(i=1;i1&(i+1)%2==0){
打印(“:”);
}  
印刷(一美元);
}
}'
您可以:

sed -i 's/\(\w\{2\}\)/\1:/g' file
这还将在字符串的末尾追加:。由于我们不能在sed regex语法中使用正向前瞻,因此我们需要:

sed -i 's/:$//g' file
请注意,我们对sed使用了就地编辑,因此文件将以这种方式更改

或者,您可以使用perl来使用一个正则表达式,该正则表达式应该是/(\w{2})(?=\w{2})/$1:/g

太多的边缘情况 Sed不是这项工作的理想工具,因为有太多的边缘案例。如果您有非常规则的数据和已知的语料库,那么这很好,但在某些情况下,您需要一些更强大的功能,在匹配/捕获感兴趣的文本后,可以独立地作用于行的各个部分。例如,给定一个包含以下内容的输入文件:

foo 1bc1034gf45dna22 bar
您可能需要提取第二列,对其进行转换,然后将其替换到位。您可以使用Ruby执行以下操作:

$ echo 'foo 1bc1034gf45dna22 bar' |
ruby -pe '
  if /(?<str>\p{Alnum}{16})/ =~ $_
    $_.sub!(str, str.scan(/../).join(?:))
  end'
这可能适用于您(GNU-sed):


嗯,暴力手段总是有的:

sed 's/\<'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\>/\1:\2:\3:\4:\5:\6:\7:\8/g'
sed的/\/\1:\2:\3:\4:\5:\6:\7:\8/g'
在续行上没有前导空格的情况下,shell将字符串正确地粘贴在一起。

sed -e 's/../&:/g' -e 's/:$//' a.txt > b.txt


是否为您工作?

我已经尝试过sed的/\w{2}/\w{2}:/g'a.txt>b.txt,其中a.txt有1BC1034GF45DNA22请注意,我正在所有人身上尝试这一点,您有许多答案可以证明是有效的。如果它们对您不起作用,那么您需要通过工具的版本号和一些逐字记录的错误消息来改进您的问题。字符串将始终更改,这只是一个示例字符串。我正在AIX上运行它,并给出了:-sed:unligal option--r用法:sed[-n][u]Script[File…]sed[-n][u][e Script e]。。。[-f脚本文件]。。。[File…]我正在AIX上运行它,并给出了:-sed:invalize选项--I用法:sed[-n][u]Script[File…]sed[-n][u][e Script]。。。[-f脚本文件]。。。[文件…]您好,我正在AIX上运行这个&我不确定ruby是如何工作的。它给出了一些ruby错误。在shell脚本中是否有其他方法可以执行此操作?@user2753366您会遇到什么错误?这甚至可以在busybox版本的
sed
下工作。它的输出与它相同。
sed 's/\<'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\([0-9a-z][0-9a-z]\)'\
'\>/\1:\2:\3:\4:\5:\6:\7:\8/g'
sed -e 's/../&:/g' -e 's/:$//' a.txt > b.txt
sed -e 's/\(..\)/\1:/g' -e 's/:$//' a.txt > b.txt