使用SED正则表达式用数字替换某些字母

时间:2015-06-01 11:27:48

标签: regex bash shell awk sed

经过一些事情我觉得非常复杂,我对正则表达式非常糟糕,所以你们可以帮忙。

请参阅此数据来源:

User ID:    
a123456
a12345f
a1234e6
d123d56
b12c456
c1b3456
ba23456

基本上,我想要做的是使用正则表达式/ sed将所有字母的出现替换为数字,除了第一个字母。字母将始终与其字母位置匹配。例如a = 1,b = 2,c = 3等。

所以结果集应如下所示:

    User ID:
    a123456
    a123456
    a123456
    d123456
    b123456
    c123456
    b123456

除了a-j之外,永远不会有任何字母,字符串总是7个字符长。

任何人都能解开一些光明吗?谢谢! :)

5 个答案:

答案 0 :(得分:3)

以下是使用标准工具cutpastetr执行此操作的一种方法:

$ paste -d'\0' <(cut -c1 file) <(cut -c2- file | tr 'abcdef' '123456')
a123456
a123456
a123456
d123456
b123456
c123456
b123456

这使用空字符串将行的第一个字符与行的其余部分的tr的结果连接起来。 tr将第一个列表中的每个元素替换为第二个列表中的相应元素。

答案 1 :(得分:3)

使用a-j替换除第一个字母以外的相应数字的一行中的perl个字词:

$ perl -pe 'substr($_, 1) =~ tr/a-j/0-9/' input_file

a=0,而不是a=1,因为j将是10(两位数)。

  

J = 0,不,只使用数字0-9,字母只是替换它们的数字对应物,所以永远不会有后者大于j。

制作j=0a=1

$ perl -pe 'substr($_, 1) =~ tr/ja-i/0-9/' input_file

答案 2 :(得分:2)

sed '/[a-j][0-9a-j]\{6\}$/{h;y/abcdefghij/1234567890/;G;s/.\(.\{6\}\).\(.\).*/\2\1/;}' YourFile
  • 仅过滤“数字”
  • 提醒行(第1个字母)
  • 将所有字母更改为数字(包括第1个)
  • 添加第一种数字形式(作为缓冲区中的第二行)
  • 取第二行的第一个字母和第一行的6个,重新排序,不要保留另一个字符

答案 3 :(得分:1)

$ awk 'BEGIN{FS=OFS=""} NR>1{for (i=2;i<=NF;i++) if(p=index("jabcdefghi",$i)) $i=p-1} 1' file
User ID:
a123456
a123456
a123456
d123456
b123456
c123456
b123456

请注意,上面按原样再现标题行User ID:。到目前为止,我能说的最好,所有其他发布的解决方案都会将标题行更改为Us5r ID:,因为它们会对其进行字母到数字的转换,就像在所有后续行中一样。

答案 4 :(得分:0)

我没有看到复杂性。您的样本看起来只是想用数字1-6替换七个字符中的六个:

s/^\([a-j0-9]\)[a-j0-9]\{6\}/\1123456/

由于放在那里的数字是由位置定义的,我们不关心这封信是什么(或者即使它是一封信)。这里的缺点是我们不保留数字,但它们在样本数据中从不变化。

如果我们只想替换字母,我能想到的第一种方法就是简单地使用多个替换:

s/^\([a-j0-9]\{1\}\)[a-j]/\11/
s/^\([a-j0-9]\{2\}\)[a-j]/\12/
s/^\([a-j0-9]\{3\}\)[a-j]/\13/
s/^\([a-j0-9]\{4\}\)[a-j]/\14/
s/^\([a-j0-9]\{5\}\)[a-j]/\15/
s/^\([a-j0-9]\{6\}\)[a-j]/\16/

用特定数字替换字母,不包括第一个字母:

s/\(.\)a/\11/g

此模式将替换两个字符序列,保留第一个字符序列,因此必须为每个字母运行两次。使用保持空间我们可以存储第一个字符并使用简单的音译。棘手的部分是加入这两个部分,然后sed注入了一个不需要的换行符。

# Store in hold space
h
# Remove the first character
s/^.//
# Transliterate letters
y/jabcdefghi/0123456789/
# Exchange pattern and hold space
x
# Keep the first character
s/^\(.\).*$/\1/
# Print it
#P
# Join
G
# Remove the newline
s/^\(.\)./\1/

还在了解sed的能力:)