执行echo "123456" | grep -Eo "[[:digit:]]{1,2}"
将返回树对12
,34
,56
。
为什么它不返回12
,23
,34
,45
,56
?
答案 0 :(得分:2)
您的正则表达式不会打印出所有5对数字,因为您只要求输入三个。
您的正则表达式与[0-9][0-9]
等效,将从左开始检查该特定匹配项;因此,如果您有123456
,则步骤将类似于:
依此类推...
请注意,它不会在匹配后再次开始,否则会一遍又一遍地匹配12
...
您可以使用其他解决方案来解决您的问题。
例如,如果您需要该字符串中的所有对,则可以使用带有前两个数字的函数。剪掉第一个,然后再次检查,直到字符串太短...
#!/bin/bash
check_pairs() {
local str="${1}"
if [ "${#str}" -ge 2 ]; then
printf "%s\n" "${str}" | sed -e "s/^\([0-9][0-9]\).*$/\1/"
check_pairs "${str#?}"
fi
}
check_pairs "123456"
exit 0
可能还有其他解决方案(更好,更快,更强大),但我现在无法想到它们。
答案 1 :(得分:1)
虽然您已经有了一个有效的答案,但是如果您的shell是bash
(或另一个允许字符串索引的高级shell),那么使用bash内置的字符串索引会更有效
for
循环以给定的字符串输出每一对,而不是在通过调用sed
创建的每次循环迭代中生成单独的子shell。
Bash字符串索引允许您使用以下格式访问以len
索引(其中有效索引为start
)开头的字符串中的0 - len-1
个字符:
${var:$start:$len}
结合C风格的for
循环循环遍历从索引i
开始的字符串中的每个索引1
(第二个字符),并输出由以下命令创建的一对字符:< / p>
"${var:$((i-1)):2}"
一个简短的例子是:
str=123456
for ((i = 1; i < ${#str}; i++)); do
echo "${str:$((i-1)):2}"
done
使用/输出示例
$ str=123456; \
for ((i = 1; i < ${#str}; i++)); do echo "${str:$((i-1)):2}"; done
12
23
34
45
56
仔细检查一下,如果还有其他问题,请告诉我。