匹配字符串中所有匹配字符的位置与bash中的正则表达式

时间:2013-04-23 14:40:14

标签: regex bash hex match

我正在尝试通过regexp匹配特定字符的所有位置。我可以使用 expr index 执行此操作,但这只匹配字符串中的第一个字符。

echo $(expr index "$z" '[\x1F\x7F-\x9F]') 

注意:$ z是包含字符串

的var

这(正确)返回:

6

我知道在这个字符串中我在第6和第12位有两个匹配的字符,我希望返回匹配字符的所有位置,而不仅仅是第一个。

你可以帮帮我吗? 谢谢!

2 个答案:

答案 0 :(得分:2)

这是使用awk的命令。它会打印与正则表达式/0-9/

匹配的所有位置
echo $z | awk  '{s=$0; i=1; idx=0; 
       while(i>0){ 
           i=match(s, /[0-9]/); 
           if(i>0) {
                  idx += i;
                  print idx; 
                  s=substr(s, i+1);
           }
       }
}'

答案 1 :(得分:0)

您可能喜欢使用 grep

#!/bin/bash

matches=();

# Used a "Process Substitution" because of the loop's subshell
while read match
do
    matches+=( "$match" );
done \
< <(
    printf '%s\n%s' \
        'somedata{a917am}some{8ka81a}data' \
        'awd123{ad123d}adad' \
        | grep -Eobn '\{[0-9a-z]{6}\}' # The magic is here
);

for (( i = 0; i < ${#matches[@]}; i++ ));
do
    matchRaw="${matches[$i]}";
    match="${matchRaw#*\:}";
    match="${match#*\:}";
    matchLine="${matchRaw%%\:*}";
    matchChar="${matchRaw#*\:}";
    matchChar="${matchChar%%\:*}";
    matchLength="${#match}";

    printf 'Match #%s, line %2s, char %2s, length %2s: "%s"\n' \
        "$((i + 1))" \
        "$matchLine" \
        "$matchChar" \
        "$matchLength" \
        "$match";
done

输出:

Match #1, line  1, char  8, length  8: "{a917am}"
Match #2, line  1, char 20, length  8: "{8ka81a}"
Match #3, line  2, char 39, length  8: "{ad123d}"

适用于 grep (GNU grep) 2.25

相关:

grep --help

# -E, --extended-regexp     PATTERN is an extended regular expression (ERE)
# -o, --only-matching       show only the part of a line matching PATTERN
# -b, --byte-offset         print the byte offset with output lines
# -n, --line-number         print line number with output lines

Process Substitution (from)