shell脚本中case条件控制语句的一个bug分析

所属分类: 脚本专栏 / linux shell 阅读数: 2004
收藏 0 赞 0 分享

在shell脚本中,发现case语句的一个问题。
就是指定小写字母[a-z]和大写字母[A-Z]的这种方法不管用了。

出现如下情况:

复制代码 代码如下:

[root@station1 ~]# cat case.sh
#!/bin/bash
while :
do
echo -n "input a letter: "
read var
case "$var" in
  [a-z]) echo "Lowercase letter";;
  [A-Z]) echo "Uppercase letter";;
 [0-9]) echo "Digit";;
  *) echo "Punctuation, whitespace, or other";;
esac
done
[root@station1 ~]# bash case.sh
input a letter: a
Lowercase letter
input a letter: A
Lowercase letter
input a letter: 2
Digit
input a letter: 0
Digit
input a letter: B
Lowercase letter
input a letter: y
Lowercase letter
input a letter: ^C
[root@station1 ~]#

可以看到当输入大小写字母都会输出“Lowercase letter”

就当我疑惑不解的时候,奇迹发生了。。。。

复制代码 代码如下:

[root@station1 ~]# bash case.sh
input a letter: Z
Uppercase letter
input a letter:

当输入大写Z的时候,终于出现了我们想要的结果:Uppercase letter
后来在man bash文档中也没有关于"-"代表范围的说明,值说想匹配"-",就把"-"放到[]中最前面或者最后面。
case word in [ [(] pattern [ | pattern ] ... ) list ;; ] ... esac
A case command first expands word, and tries to match it against each pattern in turn, using the same matching rules as for pathname
expansion (see Pathname Expansion below). The word is expanded using tilde expansion, parameter and variable expansion, arithmetic sub-
stitution, command substitution, process substitution and quote removal. Each pattern examined is expanded using tilde expansion, param-
eter and variable expansion, arithmetic substitution, command substitution, and process substitution. If the shell option nocasematch is
enabled, the match is performed without regard to the case of alphabetic characters. When a match is found, the corresponding list is
executed. If the ;; operator is used, no subsequent matches are attempted after the first pattern match. Using ;& in place of ;; causes
execution to continue with the list associated with the next set of patterns. Using ;;& in place of ;; causes the shell to test the next
pattern list in the statement, if any, and execute any associated list on a successful match. The exit status is zero if no pattern
matches. Otherwise, it is the exit status of the last command executed in list.

再看下面这段代码:

复制代码 代码如下:

[root@station1 ~]# cat case.sh
#!/bin/bash
while :
do
echo -n "input a letter: "
read var
case "$var" in
[a-c]) echo "Lowercase letter";;
[A-Z]) echo "Uppercase letter";;
[0-9]) echo "Digit";;
*) echo "Punctuation, whitespace, or other";;
esac
done
[root@station1 ~]# bash case.sh
input a letter: a
Lowercase letter
input a letter: b
Lowercase letter
input a letter: c
Lowercase letter
input a letter: d
Uppercase letter
input a letter: e
Uppercase letter
input a letter: ^C
[root@station1 ~]#

可以看出来它的编码方式是:aAbBcCdDeE...yYzZ
所以才会出现这种情况。这也算是一个小bug吧,如果想真的想达到我们想要的结果,可以用posix的[:upper:]。
个人想法:有时候出现这种情况也不是个坏事,或许还可以利用这个bug去做点事。

更多精彩内容其他人还在看

linux Shell入门:掌握Linux,OS X,Unix的Shell环境

这篇文章主要介绍了linux Shell入门:掌握Linux,OS X,Unix的Shell环境 ,需要的朋友可以参考下
收藏 0 赞 0 分享

shell 1>&2 2>&1 &>filename重定向的含义和区别

这篇文章主要介绍了shell 1>&2 2>&1 &>filename重定向的含义和区别,需要的朋友可以参考下
收藏 0 赞 0 分享

ssh远程执行命令方法和Shell脚本实例

这篇文章主要介绍了ssh远程执行命令方法和Shell脚本实例,本文讲解了ssh执行远程操作方法和远程执行命令shell脚本示例,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell中的${}、##和%%使用范例

这篇文章主要介绍了Shell中的${}、##和%%使用范例,本文给出了不同情况下得到的结果,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell脚本一次读取文件中一行的2种写法

这篇文章主要介绍了Shell脚本一次读取文件中一行的2种写法,本文还同时讲解了Shell读取文本文件的2种方法,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell脚本逐行读取文本文件(不改变文本格式)

这篇文章主要介绍了Shell脚本逐行读取文本文件,本文着重探讨不改变文本格式的方法读取出文件内容,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell脚本配合iptables屏蔽来自某个国家的IP访问

这篇文章主要介绍了Shell脚本配合iptables屏蔽来自某个国家的IP访问,本文利用IPdeny的IP数据,然后用Shell脚本导入iptables实现屏蔽IP访问,需要的朋友可以参考下
收藏 0 赞 0 分享

Bash脚本内置的调试方法技巧

这篇文章主要介绍了Bash脚本内置的调试方法技巧,本文介绍了调试技巧和几个调试技巧,比如输出行号的方法、只调试某段程序的方法,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell、Perl、Python、PHP访问 MySQL 数据库代码实例

这篇文章主要介绍了Shell、Perl、Python、PHP访问 MySQL 数据库代码实例,本文分别给出这几种语言访问Mysql数据的代码实例,需要的朋友可以参考下
收藏 0 赞 0 分享

Shell脚本计算字符串长度和判断字符串为空小技巧

这篇文章主要介绍了Shell脚本计算字符串长度和判断字符串为空小技巧,本文分别给出计算字符串长度和判断字符串为空各3种实现方法,需要的朋友可以参考下
收藏 0 赞 0 分享
查看更多