Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

bashのシェル変数の文字列パターンマッチングをするには?

6,002 views
Skip to first unread message

Takahiro Yamaguchi

unread,
Oct 29, 2006, 6:55:32 AM10/29/06
to

山口と申します。

roswell:/tmp yama$ uname -a
Darwin roswell 7.9.0 Darwin Kernel Version 7.9.0: Wed Mar 30 20:11:17 PST 2005; root:xnu/xnu-517.12.7.obj~1/RELEASE_PPC Power Macintosh powerpc
roswell:/tmp yama$ bash --version
GNU bash, version 2.05b.0(1)-release (powerpc-apple-darwin7.0)
Copyright (C) 2002 Free Software Foundation, Inc.

の環境で、

SHELL変数内に、ある文字列パターン(DUMMY)が含まれているかを調べるのに、

SYSTEML=./DUMMY/system/local

echo $SYSTEML | grep DUMMY >/dev/null 2>&1

if [ $? -eq 0 ]; then
echo EXIST
else
echo NON EIST
fi

のように書いていますが、grep を使わずに bash の機能だけ、パターンマッチング
出来るのでしょうか?

御教授よろしくお願いします。

NIDE Naoyuki

unread,
Oct 29, 2006, 8:29:30 AM10/29/06
to
In article <m2k62j8hfv.wl%yama...@u08.itscom.net>,

yama...@u08.itscom.net writes:
> のように書いていますが、grep を使わずに bash の機能だけ、パターンマッチング
> 出来るのでしょうか?

case "$SYSTEML" in
*DUMMY*)

;;
esac

という手が使えますね。正規表現は使えませんが。bashでなくてもいけます。

ni...@ics.nara-wu.ac.jp

Shinji KONO

unread,
Oct 29, 2006, 10:01:19 AM10/29/06
to
河野真治 @ 琉球大学情報工学です。

In article <0610292229...@hayabusa.ics.nara-wu.ac.jp>, ni...@ics.nara-wu.ac.jp (NIDE Naoyuki) writes


> case "$SYSTEML" in
> *DUMMY*)
> …
> ;;
> esac
> という手が使えますね。正規表現は使えませんが。bashでなくてもいけます。

bash だから、[[]] 中に正規表現が使えます。== != でも使えるので、

In article <m2k62j8hfv.wl%yama...@u08.itscom.net>,Takahiro Yamaguchi <yama...@u08.itscom.net> writes


> SYSTEML=./DUMMY/system/local
> echo $SYSTEML | grep DUMMY >/dev/null 2>&1
> if [ $? -eq 0 ]; then
> echo EXIST
> else
> echo NON EIST
> fi


SYSTEML=./DUMMY/system/local
if [[ $SYSTEML == *DUMMY* ]]; then


echo EXIST
else
echo NON EIST
fi

ですね。zsh でも、Ok。ほとんど、すべてのshは、bashだったりするから、
実は、ほとんどOkってことだな。

---
Shinji KONO @ Information Engineering, University of the Ryukyus
河野真治 @ 琉球大学工学部情報工学科

NIDE Naoyuki

unread,
Oct 29, 2006, 11:04:15 AM10/29/06
to
In article <3993296...@rananim.ie.u-ryukyu.ac.jp>,

ko...@ie.u-ryukyu.ac.jp writes:
> if [[ $SYSTEML == *DUMMY* ]]; then

それじゃ正規表現ではないのでは? 単なるシェルのメタ文字。

でも、bashの場合(バージョン2から?)はshopt -s extglobすると、パターンマッ
チングが拡張されて、正規表現相当のこと(選択も反復も、もちろん連接もあり)
を書けるようになるみたいですね。

shopt -s extglob
[[ ababcdabx == *(ab|cd)x ]] && echo ok

がokを出力する。うーん、知らなかった。記法は普通とちょっと違ってて、反復
の「*」などを前置しなければならなかったりするけれど。
但し、shoptはその行が構文解析されてから実行されるので、

shopt -s extglob; [[ ababcdabx == *(ab|cd)x ]] && echo ok

ではだめ。

> ですね。zsh でも、Ok。ほとんど、すべてのshは、bashだったりするから、

そりゃ乱暴な。でも、元記事の人の環境ならshがbashなことを仮定してもいいの
かな。よく知りませんが…
ni...@ics.nara-wu.ac.jp

Shinji KONO

unread,
Oct 29, 2006, 5:15:19 PM10/29/06
to
河野真治 @ 琉球大学情報工学です。

In article <0610300104...@osabishi.ics.nara-wu.ac.jp>, ni...@ics.nara-wu.ac.jp (NIDE Naoyuki) writes


> そりゃ乱暴な。でも、元記事の人の環境ならshがbashなことを仮定してもいいの
> かな。よく知りませんが…

またまた...今回は、bash と明記されているので、こだわる必要は
ないんですけどね。

珍しく man bash で見つかったけど、ここでRTFMというのは、
不粋だろうな。

> 但し、shoptはその行が構文解析されてから実行されるので、
>
> shopt -s extglob; [[ ababcdabx == *(ab|cd)x ]] && echo ok
>
> ではだめ。

知っている人は、「なるほど」と納得するわけなんだけど、bash
らしい、adhoc な拡張/実装ですね。僕だったら、hoge =~ "(ab|cd)*"
みたいな仕様にして逃げるだろうけど。

zsh だと、

setopt EXTENDED_GLOB
if [[ $foo = (a|an)' '(#b)(*)' '* ]]; then
print ${foo[$mbegin[1],$mend[1]]}
fi

などという例があるなぁ。default で入れておくか...

そういえば、zsh に移った理由の一つが [^a-z] が使えること
だったはず。その割りには使ってない。そんなものだ。

Masamichi Takatsu

unread,
Oct 29, 2006, 9:06:03 PM10/29/06
to
たかつです。

shell での解決法は既に書かれてるので、別の話。

記事 <m2k62j8hfv.wl%yama...@u08.itscom.net> で
Takahiro Yamaguchiさんは書きました

> echo $SYSTEML | grep DUMMY >/dev/null 2>&1

こういう時は、 grep の -q オプションが便利ですよ。
・出力の抑制
・マッチ1行目で即終了
です。こういうスクリプトではあまりメリット無いですが、
長いファイルの中にある特定の文字列が含まれてるかどうかを
チェックする時は、マッチしたらすぐ終了するのは便利です。
マッチしない時は結局ファイルを全部スキャンするわけですが…

私はシステム監視系のスクリプトで、
if ps -ax | grep -q -s "[0-9] sendmail: accepting" ; then
(以下略)
なんてのをよくやってます。

PROJECT TEAM DoGA 高津正道 ta...@doga.jp
TBD0...@nifty.ne.jp
PROJECT TEAM DoGAのホームページ → http://doga.jp/
10月30日(月) 今日のマーフィーの法則 [アンソニーの作業場の法則]
作業場で道具を落とすと、もっともやっかいな場所に転がり込む。

Hideo Sir MaNMOS Morishita

unread,
Oct 30, 2006, 2:11:05 AM10/30/06
to

In article <0610301106...@XP.doga.jp>,

Masamichi Takatsu <ta...@doga.jp> writes:
> たかつです。
>
> shell での解決法は既に書かれてるので、別の話。
>
> 記事 <m2k62j8hfv.wl%yama...@u08.itscom.net> で
> Takahiro Yamaguchiさんは書きました
>
> > echo $SYSTEML | grep DUMMY >/dev/null 2>&1
>
> こういう時は、 grep の -q オプションが便利ですよ。
> ・出力の抑制
> ・マッチ1行目で即終了

Solarisの/usr/bin/grepにはそれが無いの…しくしく。

#/usr/xpg4/bin/grepでいいんですけど。

--
___ わしは、山吹色のかすてーらが大好きでのぅ
[[o o]] ふぉっふぉっふぉ
'J' 森下 お代官様 MaNMOS 英夫@ステラクラフト
PGP Finger = CD EA D5 A8 AD B2 FE 7D 02 74 87 52 7C B7 39 37

Takahiro Yamaguchi

unread,
Oct 30, 2006, 10:22:31 AM10/30/06
to

河野様

At Sun, 29 Oct 2006 15:01:19 +0000 (UTC),
Shinji KONO wrote:

[...]

>
> bash だから、[[]] 中に正規表現が使えます。== != でも使えるので、

man で Pattern Matching までは分かっていたのですが...
Pathname Expansion の項にあったので、

> if [[ $SYSTEML == *DUMMY* ]]; then

このように使うのは、読み切れませんでした。
これで、ちょっとはエレガントにシェルスクリプトが書けます。

御教授いただきありがとうございました。

# 河野様
# 以前、通堂(とんどう) を紹介してもらった山口です。
#「おんな味」食べましたけどあっさりしておいしかったです。

Takahiro Yamaguchi

unread,
Oct 30, 2006, 10:26:18 AM10/30/06
to

高津様

山口です。

At Mon, 30 Oct 2006 02:06:03 GMT,
Masamichi Takatsu wrote:

[...]

>
> > echo $SYSTEML | grep DUMMY >/dev/null 2>&1
>
> こういう時は、 grep の -q オプションが便利ですよ。
> ・出力の抑制
> ・マッチ1行目で即終了
> です。こういうスクリプトではあまりメリット無いですが、
> 長いファイルの中にある特定の文字列が含まれてるかどうかを
> チェックする時は、マッチしたらすぐ終了するのは便利です。
> マッチしない時は結局ファイルを全部スキャンするわけですが…

目から鱗状態です。
やっぱり man をもっと読み込まないとなあ... と感じました。
ありがとうございます。

0 new messages