Bash-遍历字符串中的每个字符以检查特定模式

时间:2014-09-27 13:51:17

标签: regex string bash loops character

所以我需要检查字符串中的每个字符 - 输入 - 以查看它是否匹配/不匹配模式。

在Codelish中:

我猜我是否必须使用for循环?

在for循环中会有 -

    for each character in string
    do (the following)
    if it doesn't contain one/more number
    echo it doesn't contain contain one/more number
    fi
    [then other conditions]
    done.

所以我要做的就是分析字符串中的每个字符并显示错误消息msg(对于每个条件)作为输出。

非常感谢任何帮助。

1 个答案:

答案 0 :(得分:1)

如上所述,通过char循环字符串char通常是一种非常有效的策略。但是这是使用awk做到这一点的一种方法。下面的程序确定输入文件每行中每个字符的字符类。有关character classes的确切定义,请参阅awk手册。

<强> CharTypes0.awk

#!/usr/bin/awk -f

# Print the character class of each character in each input line
# Written by PM 2Ring 2014.10.02

BEGIN{numtypes = split("lower upper digit punct blank", types); FS = ""}

{
    for(i=1; i<=NF; i++)
        for (j=1; j<=numtypes; j++)
        {
            type = types[j]
            if ($i ~ "[[:" type ":]]")
            {
                printf "'%s': %s\n", $i, type
                break
            }
        }
}

您可以像这样运行此程序:

echo 'This is A $24 @test.' | awk -f CharTypes0.awk

<强>输出

'T': upper
'h': lower
'i': lower
's': lower
' ': blank
'i': lower
's': lower
' ': blank
'A': upper
' ': blank
'$': punct
'2': digit
'4': digit
' ': blank
'@': punct
't': lower
'e': lower
's': lower
't': lower
'.': punct

或者您可以通过在命令行上命名它们来处理一个或多个文本文件的所有行,例如:

awk -f CharTypes0.awk test1.txt test2.txt

.....

这个程序的一个更高效的版本可以很容易地计算整个单词或行中每种类型的字符数,而不是循环遍历每个字符。


修改

例如,

<强> CountCharTypes0.awk

#!/usr/bin/awk -f

# Count number of characters in each input line that match various classes
# Written by PM 2Ring 2014.10.01

BEGIN{numclasses = split("lower upper alpha digit alnum punct blank", classes)}

{
    printf "\nData:[%s] Length: %d\n", $0, length($0)
    for (i=1; i<=numclasses; i++)
    {
        class = classes[i]
        printf "%s %2d\n", class, gsub("[[:" class ":]]", "&")
    }
}

CharTypes0.awk


修改2

这是CharTypes的纯粹bash版本:

#!/bin/bash

# Print the character class of each character in $1
# Written by PM 2Ring 2014.10.03
chartypes()
{
    types=(lower upper digit punct blank)

    string=$1

    for((i=0; i<${#string}; i++))    
    do
        ch=${string:i:1}
        for t in ${types[@]}
        do
            [[ $ch =~ [[:${t}:]] ]] &&
            { echo "[$ch] $t"; break; }
        done
    done
}

chartypes 'This is A $24 @test.'