条件if语句不起作用

时间:2015-02-10 05:18:54

标签: arrays bash

我想检查用户输入和检查的所有字符,而不是最后一个字符是空格字符。这就是我所拥有的:

lastEle="${#charArr[@]}"
lastEle=$((lastEle - 1))
for f in "${charArr[@]}" ; do
    if [[ "$f" != "${charArr["$lastEle"]}" && "$f" == " " ]] ; then        #'if' 
        abort "1" "$LINENO"    "Strings cannot contain space characters and at least one was detected in the input string" "exit"        #funct call
    fi
done

1。确定字符数组的最后一个元素的索引号 2. for循环用于循环通过每个数组元素
3.如果条件用于确定被检查的元素是否是最后一个元素,如果不是,则$ f元素的字符不是空格“”字符
4.如果任何元素的条件不为真,则调用函数abort退出脚本

if条件似乎没有按照写入的方式工作,因为当我输入一个包含至少一个空格char的字符串时脚本不会退出,并且我确定abort函数正常工作。我确信问题是我的一些轻微疏忽,但对于我的生活,我看不到它。如果有人不介意权衡开导我会很感激。

2 个答案:

答案 0 :(得分:1)

这个怎么样?你必须稍微修改一下代码。

        input="Test string "
        if [[ `echo $input | sed 's/ *$//g' | grep -o " " | wc -l` > 0 ]]
        then
                echo "Strings cannot contain space characters and at least one was detected in the input string"
        else
                echo "Good string"
        fi

答案 1 :(得分:1)

这对我来说似乎有点过分了。

如果您只是想检测用户是否输入了包含不在末尾(a)的任何空格的字符串,只需使用bash替换工具:

$ x="hello";        if [[ "${x/ [^ ]/}" != "$x" ]]; then echo bad; fi

$ x="hello ";       if [[ "${x/ [^ ]/}" != "$x" ]]; then echo bad; fi

$ x="hello there";  if [[ "${x/ [^ ]/}" != "$x" ]]; then echo bad; fi
bad

$ x="hello there "; if [[ "${x/ [^ ]/}" != "$x" ]]; then echo bad; fi
bad

替换只会找到space的第一个序列,然后是nonspace,然后将其删除。变量展开${x/ [^ ]/}表示:

  • 接受变量$x
  • 找到第一次出现" [^ ]"(空格后跟非空格)。
  • 用空字符串替换它(即删除它)。

如果 删除它,则该字符串将与原始字符串不同,因此if语句将“激活”。


就你为什么不起作用而言,它完全取决于charArr实际上是什么。如果它是一个字符串:

charArr="hello pax"

或:

read charArr

然后将set -x放在脚本顶部会向您显示完全问题所在:

+ charArr='hello pax'
+ lastEle=1
+ lastEle=0
+ for f in '"${charArr[@]}"'
+ [[ hello pax != \h\e\l\l\o\ \p\a\x ]]

换句话说,它是不是一个字符数组,而是一个一个字符串的数组。

实际上使用真实的字符数组:

charArr[0]="h"
charArr[1]="e"
charArr[2]="l"
charArr[3]="l"
charArr[4]="o"
charArr[5]=" "
charArr[6]="p"
charArr[7]="a"
charArr[8]="x"

将导致输出似乎有效(尽管我的环境中没有abort函数/程序):

+ charArr[0]=h
+ charArr[1]=e
+ charArr[2]=l
+ charArr[3]=l
+ charArr[4]=o
+ charArr[5]=' '
+ charArr[6]=p
+ charArr[7]=a
+ charArr[8]=x
+ lastEle=9
+ lastEle=8
+ for f in '"${charArr[@]}"'
+ [[ h != \x ]]
+ [[ h == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ e != \x ]]
+ [[ e == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ l != \x ]]
+ [[ l == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ l != \x ]]
+ [[ l == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ o != \x ]]
+ [[ o == \  ]]
+ for f in '"${charArr[@]}"'
+ [[   != \x ]]
+ [[   == \  ]]
+ abort 1 16 'Strings cannot contain space characters and at least one was detected in the input string' exit
testprog.sh: line 16: abort: command not found
+ for f in '"${charArr[@]}"'
+ [[ p != \x ]]
+ [[ p == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ a != \x ]]
+ [[ a == \  ]]
+ for f in '"${charArr[@]}"'
+ [[ x != \x ]]

无论如何,我认为检测字符串结尾的逻辑从一开始就是错误的。如果字符是agbc efg,那么它实际上将停在第二个字符,因为您的检查只是“这个字符是否等于数组中的最后一个字符?”。因此,你永远不会在c之后找到那个空格。


(a)请注意,定义很好,它包括那些在末尾有多个空格的有效字符串,例如"hello<space><space>"

如果您想要那样,您可以选择以下测试:

if [[ ! $x =~ ^[^\ ]*\ ?$ ]]; then echo bad; fi

基本上检查以确保整个变量(使用^$锚点)由零个或多个非空格组成([^\ ]*)后跟一个可选空格(\ ?)。