トップページunix
985コメント289KB

シェルスクリプト総合 その8

■ このスレッドは過去ログ倉庫に格納されています
0001名無しさん@お腹いっぱい。2007/02/15(木) 14:28:44
シェルスクリプトの総合スレです。
スクリプトのお勉強・自慢・腕試しなどにどうぞ。
まずは注意点、リンク、地鎮祭など(>>1-6くらい)をご覧ください。


□お約束
・特記なき場合はBourne Shell(/bin/sh)がデフォルトです。
 bash/zsh/ksh/ashなどに依存する場合は明示しましょう。
 Linuxユーザは/bin/shの正体がbashなので特に注意。
・csh/tcshのシェルスクリプトは推奨されません。
(理由は「csh-whynot」でググれ)
・UNIXにはシェルスクリプトに便利な小さなコマンドがいろいろあります。
 manや参考リンクを見ましょう。
 aproposないしはman -kでそれらしい単語による簡単な検索もできます。
・シェルスクリプトのことをシェルってゆーな
・シェルで使えるワイルドカード等は正規表現ではありません。
正規表現の話題はスレ違い(正規表現スレへ)

□初心者へのアドバイス:
・適した道具を判断するのも頭の重要な使い方。シェルスクリプトよりも
 RubyやPerlの方が適した仕事には素直にそちらを使いましょう。
・知らないコマンドが出てきたらmanを引きましょう。
・思い通りに動かないときは、まずは sh -x でトレースしましょう。

前スレ
シェルスクリプト総合 その7
http://pc10.2ch.net/test/read.cgi/unix/1157601611/
0679名無しさん@お腹いっぱい。2007/06/22(金) 00:04:29
ケータイでも3G(高周波のやつ)は大丈夫らしいけど。
0680名無しさん@お腹いっぱい。2007/06/22(金) 09:16:46
使えない奴にかぎって、くだらねえことに拘ってたりする
0681名無しさん@お腹いっぱい。2007/06/22(金) 20:12:44
そろそろUNIXの話にでも戻す?
0682名無しさん@お腹いっぱい。2007/06/22(金) 20:59:20
よしなに
0683名無しさん@お腹いっぱい。2007/06/22(金) 23:11:19
>>678
>>準拠したからって売れ行きがたいして変わるわけでもないし。

売行きが変わらないからって騒ぐこともないでしょ。
拘りがなければ準拠する方がはるかに楽なのにねぇ

あくまで /bin/sh 標準なのは基本であって、実勢はケースバイケースで、
linux じゃ bash 標準だろうし、 solaris だって適宜 ksh なり使うだろうし、
パーソナルユースや $HOME/bin 限定使用とか、管理者でも同一プラット
ホームだけでの運用が多く、移植性のプライオリティーがさほど高くない
現況において、やいのやいのいう奴は要するに「言いたいだけ」ちゃうんかと。
0684名無しさん@お腹いっぱい。2007/06/22(金) 23:53:48
> 拘りがなければ準拠する方がはるかに楽なのにねぇ

何が楽なのか詳しく書いて欲しいんだが。

商用ソフトってちょっと変えると、検証がスゲー大変なことぐらいは知ってるよな?
0685名無しさん@お腹いっぱい。2007/06/23(土) 00:08:17
楽しいもの見つけてしまった。

http://sed.sourceforge.net/sed1line.txt
http://www.student.northpark.edu/pemente/awk/awk1line.txt

組込みで使っているLinuxにgrepが入ってなくて
sedでシミュレートしたスクリプト書いたんだけど、
それ以上のことがいろいろできそうな感じなり。


おまけ

http://www.fepus.net/ruby1line.txt
0686名無しさん@お腹いっぱい。2007/06/23(土) 00:11:08
>>683
Solarisは古いshとkshを選択できるからいいけど、
HP-UXとかAIXは/bin/shはkshそのもなんで選択の余地はない。

シェルごときで移植性とか言ってるアホが多いっていうのは同意。
0687名無しさん@お腹いっぱい。2007/06/23(土) 03:31:47
視野が狭いのって、幸せでいいよね。
0688名無しさん@お腹いっぱい。2007/06/23(土) 08:31:29
そう?いまどきシェルの互換性なんか気にしてる奴って幸せそうに見えないが。
0689名無しさん@お腹いっぱい。2007/06/23(土) 09:38:27
シェルはさまざまなコマンドと組み合わせて使うしな。
コマンドにも完全な互換性がない以上、シェルスクリプトの互換性や移植性を気にし過ぎるのはアホ。
ささっと書いてテストして動きが変だったら、そのとき直せばいい。
シェルってそういうライトな使い方をするためのものでしょ。
0690名無しさん@お腹いっぱい。2007/06/23(土) 10:04:55
互換性のことも知らずに、暢気に
[ -e file ] とか、export HOGE=hoge とか書いて、
「動いたからOK」とか言ってる香具師の方がアフォに見えるけどな。
0691名無しさん@お腹いっぱい。2007/06/23(土) 10:28:19
「さくっと直せばいいじゃん」って言ってる奴はだいたい直したことがない奴だし。
0692名無しさん@お腹いっぱい。2007/06/23(土) 10:32:04
そもそも、直す必要なんてない、動くから
0693名無しさん@お腹いっぱい。2007/06/23(土) 11:05:10
>>692
>>690
0694名無しさん@お腹いっぱい。2007/06/23(土) 11:08:34
何が問題か、具体的に
0695名無しさん@お腹いっぱい。2007/06/23(土) 12:54:51
問題を理解できていないことが問題なんだろ。
0696名無しさん@お腹いっぱい。2007/06/23(土) 13:08:14
互換性がいるのは移植する可能性がある場合だろうかと。
あるいは環境が一部不明な場合か。
ただ、知識としてはあれば有効だろうが
0697名無しさん@お腹いっぱい。2007/06/23(土) 14:23:00
開発当初は特定のシステム限定であったとしても、実社会では
いつのまにかそんな制約はなくなってしまうものなのだよ。

ニートにはわからないだろうが。
0698名無しさん@お腹いっぱい。2007/06/23(土) 14:53:17
自分の体験したことが、現実の全てだと思っている>>697がいるスレはここですか?
0699名無しさん@お腹いっぱい。2007/06/23(土) 15:16:00
>>698
「全ての」と「存在する」の違いを未だ習ってないのかい? ぼーや
0700名無しさん@お腹いっぱい。2007/06/23(土) 15:20:19
シェルで移植性の高いスクリプトを書くのはめんどうくさいので
Perlを使うようになりますた
0701名無しさん@お腹いっぱい。2007/06/23(土) 16:25:18
それはそれで別の移植性の低さが問題になりそうな…
0702名無しさん@お腹いっぱい。2007/06/23(土) 16:36:58
Solarisさえ無くなればシェルの互換性の問題はほとんど解決するよね。
0703名無しさん@お腹いっぱい。2007/06/23(土) 16:55:08
UNIXのソフト開発標準を策定しようという取り組みはたくさんあった。
だがそうした標準は、POSIX(Portable Operating System Interface)のように
一般的過ぎて役に立たないか、あるいはUNIX戦争として知られる
Open Software Foundation対UNIX Internationalの企業連合間抗争に
巻き込まれるかだった。
0704名無しさん@お腹いっぱい。2007/06/23(土) 17:09:49
mkmfのようにメタスクリプトを環境依存シェルスクリプトにコンパイルする
プログラムがあるといいと思います!
0705名無しさん@お腹いっぱい。2007/06/23(土) 17:11:11
mkmfって、、また古い遺物を持ち出してきたなぁ、、
0706名無しさん@お腹いっぱい。2007/06/23(土) 20:29:52
本当にそんな互換性が必要ならlintの一つや二つとっくにありそうな気がするが、
寡聞にして知らないなあ。
0707名無しさん@お腹いっぱい。2007/06/23(土) 20:33:44
>>706
つ dash #まあ呼び出したコマンドの互換性まではチェックできないわけだが・・・
0708名無しさん@お腹いっぱい。2007/06/23(土) 20:36:48
役に立たない、ただそれだけ
0709名無しさん@お腹いっぱい。2007/06/24(日) 05:17:26
すべてのシェルが/bin/shを名乗るのを止めて
/bin/shを永久欠番化すれば解決
0710名無しさん@お腹いっぱい。2007/06/25(月) 02:26:09
なんかすごい扱われようだな。
互換性を述べている人は割とバランスの取れたUNIX流の解釈だと思うぞ
0711名無しさん@お腹いっぱい。2007/06/25(月) 03:02:50
どうせUnixなんて適当じゃねえか
varとかetcとか
システム変えることになったらどうせテンヤワンヤだ
0712名無しさん@お腹いっぱい。2007/06/25(月) 05:49:56
ということにしたいんですね:)
0713名無しさん@お腹いっぱい。2007/06/25(月) 23:17:51
>>710
素直に自分よりの解釈だと言えば?
0714名無しさん@お腹いっぱい。2007/06/25(月) 23:43:08
>>685のは結構凄いと思うが、
>>517のedのヤツはもっと凄いな。
オレもed好きになろう。
0715名無しさん@お腹いっぱい。2007/06/26(火) 15:37:00
edで日本語がうまく扱うほうほうがあれば言うことないのだが・・・・
0716名無しさん@お腹いっぱい。2007/06/26(火) 15:40:11
sedにin-placeオプションがなくてperlをよく知らなかったころは
edでやってたな
0717名無しさん@お腹いっぱい。2007/06/26(火) 15:40:12
>715
edより先におまえが日本語をうまく扱えるようになる必要がありそうだ
0718名無しさん@お腹いっぱい。2007/06/26(火) 15:44:41
誰がうまいこといえと
0719名無しさん@お腹いっぱい。2007/06/26(火) 21:37:41
てか、蒸し返すようで恐縮だけど
シェルスクリプトって、基本的に ash と ksh と bash で動けば
移植性で問題になることは極めて低いよね?

この三つで動いても駄目な環境って今どれほど実運用されているのだろうか?
0720名無しさん@お腹いっぱい。2007/06/26(火) 23:39:23
>>719
Solarisが問題だな。Solarisにはkshが標準で付いてるとは言え、
シングルユーザモードでは使えない。
シングルユーザモードを含めたシステムスクリプトは依然、
/bin/shか/sbin/sh(単にstatic linkというだけで中身は/bin/shと同じ)の
範囲内で書く必要がある。
誰かが書いてたように、Solarisが無くなる(もしくは影響力が無くなる)なら、
シェルの互換性の問題は一気に解決するだろう。
0721名無しさん@お腹いっぱい。2007/06/27(水) 00:25:59
Solarisの/binは/usr/binへのシンボリックリンクだからkshやbash使ってもいいんじゃない?
/usr/binの中には/bin/kshで書かれたコマンドもけっこうある。
Solarisのshの動きがヘンなのはたしかにときどきちょっと困る。
0722名無しさん@お腹いっぱい。2007/06/27(水) 00:42:18
> Solarisの/binは/usr/binへのシンボリックリンクだから

マジで?
0723名無しさん@お腹いっぱい。2007/06/27(水) 00:46:28
> シングルユーザモードでは使えない。
> シングルユーザモードでは使えない。
> シングルユーザモードでは使えない。
0724名無しさん@お腹いっぱい。2007/06/27(水) 00:50:42
>>721
マジだよ。/sbinは別れてるけど。
>>720は/usrがマウントできない状況のことを言ってるんだと思うけど最近は/と/usrを分けないのもふつうなんじゃないかな。
0725名無しさん@お腹いっぱい。2007/06/27(水) 00:53:11
どっちかっつーとそういう問題でなくて、
ふつースクリプトは#!/bin/shで書くけど/bin/shが何だかわかんねーじゃん?
って話では?
0726名無しさん@お腹いっぱい。2007/06/27(水) 02:29:26
>>722
HP-UXもだな。
0727名無しさん@お腹いっぱい。2007/06/27(水) 02:31:28
ashもいろいろ修正入ってる。
Solarisの/bin/shはそれこそSystemV7のころのものとほとんど変わっていない。
0728名無しさん@お腹いっぱい。2007/06/27(水) 03:37:47
・・・ってシェルを使えじゃなくてPOSIXだか何かのsh規格に沿って書けって事だよな。
0729名無しさん@お腹いっぱい。2007/06/27(水) 07:44:21
>>721
じゃなくて、シングルユーザーモードの時、
/sbin/shはあるが、
/sbin/kshは無い。

/sbin/shはstatic linkの/bin/sh(/usr/bin/sh)
だから、シングルユーザーモードも含めれば、
結局 /bin/shの文法の範囲で書かざるを得ないという話。

しかも、Solarisの/bin/shは古いままなので、
export a=b も、$(command)も test -e も、
ちょっと新しい書き方はすべて使えない。
0730名無しさん@お腹いっぱい。2007/06/27(水) 08:03:47
互換性の話に便乗だけど、
一部のスクリプトで、未だに

${1+"$@"} って書いてあるのがある。
これ、もう "$@" でいいんじゃないか?

引数が0個の時に ""が残らないようにする措置だろうけど、
Solarisの/bin/shですらそんな不具合は発生しない。(確認済み)
なので、"$@"と書いて問題ないし、視認性上も "$@"と書くべきと思うんだが。

本当に ${1+"$@"}と書く必要がある /bin/shを搭載したOSって、
現存してる?
0731名無しさん@お腹いっぱい。2007/06/27(水) 22:07:07
>>729
なんか Solaris のシングルユーザモードって不便そうですね。
CD 6枚焼いたけど、インストールを躊躇してしまうよ。
0732名無しさん@お腹いっぱい。2007/06/27(水) 22:19:42
/ と /usr をわけたりしなければ気にする必要ないよ。
0733名無しさん@お腹いっぱい。2007/06/27(水) 23:07:41
>>724, >>726
なるほどねぇ、知らんかったよ。ありがと。

>>730
書き換えるのが面倒なだけなんじゃないか?

目障りだと思うなら、君が片っ端から書き換えて動作検証してあげればいいと思う。
0734名無しさん@お腹いっぱい。2007/06/27(水) 23:19:19
>>732
すんません BSD ユーザなもので、 / と /usr を分けるというのが
イマイチ良く解かりません。
ad0s1a に全部突っ込めって事ですか?
/var も /tmp も含めて・・・(よーするに swap 以外は同じパーテーション?)
Solaris だとそんなの有りなんだぁ。(BSDでも無いことは無いけど、なんだか・・)
0735名無しさん@お腹いっぱい。2007/06/27(水) 23:36:43
OSは別に関係ない。パーティションの切り方なんて好みの問題だ。
0736名無しさん@お腹いっぱい。2007/06/27(水) 23:43:05
>>735
でも、その好みの問題に対して Solaris はシングルユーザモードの
挙動をもってして、ユーザに介入してくる分けでしょう?
>>732 のレスからは、そういう風に読めるのだが?
0737名無しさん@お腹いっぱい。2007/06/28(木) 00:09:08
どうでもいいけどよそでやってくんないかな。
0738名無しさん@お腹いっぱい。2007/06/28(木) 05:10:23

>>730 の ${1+"$@"}  てどうゆう意味なの??
なんか理解できん・・・(TT
0739名無しさん@お腹いっぱい。2007/06/28(木) 05:18:04
>>734
NetBSDのデフォルトは分けないからBSDユーザーってのは言い訳にならない。
0740名無しさん@お腹いっぱい。2007/06/28(木) 07:33:15
あと、未だに
if [ X$HOGE = X ]
なんてのも見かける。これも、
if [ "$HOGE" = '' ]
と書いたほうがいい。

むかーしのバージョンのtestで、$HOGEの内容が = だったような場合、
[ = = '' ] みたいになるとエラーになるtestに対する対処として、
X$HOGE とかいう回避法があったけど、今の testコマンドでそれが必要なのは
もう現存しないはず。
0741名無しさん@お腹いっぱい。2007/06/28(木) 14:01:16
>むかーしのバージョンのtestで、$HOGEの内容が = だったような場合、

ちがう。
$HOGE の内容が -f だったような場合に対する対処だから、今でも有効。
0742名無しさん@お腹いっぱい。2007/06/28(木) 14:16:42
>>741
$HOGE の内容が -f でも正常に動くんだけど。
[ -f = hoge ] みたいに、項が3つある時は、
-fはファイル存在オプションとはみなされないから

-f だった時駄目になるような/bin/sh搭載した OSって 何?
0743名無しさん@お腹いっぱい。2007/06/28(木) 14:36:59
>>742

a="-f"
b="-a"
c="="
d=""
test X"$a" = X"$b" -a X"$c" = X"$d"
echo $?
test $a = $b -a $c = $d
echo $?

FreeBSD の ash、Solaris の sh, ksh、GNU bash いずれでも異なる結果になりました。
0744名無しさん@お腹いっぱい。2007/06/28(木) 14:39:58
>>743
それは、複数の式を -a (AND) でつないだ場合の話。
それだと確かに式の評価がおかしくなることがあるが、

[ $HOGE = hoge ] なら、X$HOGE とする必要はなし。

Solarisの/bin/sh でも [ -f = -f ] は無問題。
0745名無しさん@お腹いっぱい。2007/06/28(木) 14:43:14
-a 使ってるかどうかで場合わけするより
一律で X$HOGE にしといた方がおしゃれ。
0746名無しさん@お腹いっぱい。2007/06/28(木) 14:48:53
>>745
-a 使う場合は、各評価式ごとに \( \) で括るのを推奨。

[ \( "$a" = "$b" \) -a \( "$c" = "$d" \) ]

↑みたいにね。これで、X"$HOGE" は不要。
0747名無しさん@お腹いっぱい。2007/06/28(木) 14:54:19
>>744
> [ $HOGE = hoge ] なら、

クォート忘れてる。

> X$HOGE とする必要はなし。

ダウト。
そのへんの対バカ性能をどこまで頑張るかはヒューリスティックで実装依存。

たとえばFreeBSDのtestでは

$ HOGE='!'
$ [ "$HOGE" = hoge ]; echo $?
[: =: unexpected operator
2

となるので変数に任意の値を想定するなら "X$HOGE" = Xhoge は依然必要。
常にtestの引数が正しい式となるよう書くにしくはなし。
0748名無しさん@お腹いっぱい。2007/06/28(木) 15:06:47
>>747 氏に聞きたいのだが、
>>730 についてはどうお考え?

${1+"$@"} は以前必要? もう不要で "$@"で桶?
0749名無しさん@お腹いっぱい。2007/06/28(木) 15:09:08
ここでポリシー決めても
どこ使うんだろ。
0750名無しさん@お腹いっぱい。2007/06/28(木) 17:18:00
こういう突っ込んだ話まで網羅してる本は無いの?
0751名無しさん@お腹いっぱい。2007/06/28(木) 17:20:30
結局トラディショナルな書式に落ち着くんだよな...
0752名無しさん@お腹いっぱい。2007/06/28(木) 17:25:52
文字列の比較なら [ X"$HOGE" = hoge ] なんてするより
case $HOGE in hoge) にするなぁ。

caseだと、たとえ$HOGEの中身が ! だとか -f -a とか特殊記号だったとしても
すべて無問題だから。
0753名無しさん@お腹いっぱい。2007/06/28(木) 17:31:27
>>750
詳解シェルスクリプトを企画するか
0754名無しさん@お腹いっぱい。2007/06/28(木) 17:35:22
需要ないだろー
0755名無しさん@お腹いっぱい。2007/06/28(木) 17:37:22
wikiでいいんじゃね
0756名無しさん@お腹いっぱい。2007/06/28(木) 17:38:15
需要とかそういうことに興味あるのかしら?
0757名無しさん@お腹いっぱい。2007/06/28(木) 17:39:17
>>756
本売るつもりなら大事でしょ。
0758名無しさん@お腹いっぱい。2007/06/28(木) 17:40:07
需要ないだろ。問題になるのSolarisだけだし、Solarisユーザーの人数が、、、
0759名無しさん@お腹いっぱい。2007/06/28(木) 17:41:25
>>757
>>756 が言ってるのは、ユーザーがシェルの互換性に興味あるのか? ってことでは
(需要に興味があるかどうかじゃなく)
0760名無しさん@お腹いっぱい。2007/06/28(木) 17:49:09
今時、シェルスクリプトの本なんて、全く売れないとは言わないにしても
何冊くらい売れるんだ?
このスレでも>>4にある本の話なんて全然出ないし。
0761名無しさん@お腹いっぱい。2007/06/28(木) 17:50:30
入門書はそれなりに売れるんじゃないの?
そういうの読む人がここの話に参加しづいらいだけで。
0762名無しさん@お腹いっぱい。2007/06/28(木) 17:52:47
getopts は互換性あるの?
0763名無しさん@お腹いっぱい。2007/06/28(木) 17:59:17
>>762
よほど古いシェルじゃない限り互換性ある。でもなぜか出番なくてあまり使わない。
0764名無しさん@お腹いっぱい。2007/06/28(木) 18:02:34
詳説正規表現もこんなのみんな興味あるのかよとかおもったけど
意外に受けたらしいから
0765名無しさん@お腹いっぱい。2007/06/28(木) 18:11:11
互換性があって、どのシェルでも使えるのに、
使ってるの見たことないコマンドの筆頭が readonly だな。
0766名無しさん@お腹いっぱい。2007/06/28(木) 18:12:21
>>763
ありがとうございます。
もうひとつ質問なんですが、ポータブルかつ安全に一時ファイルを作成するにはどうすればいいのでしょうか。
0767名無しさん@お腹いっぱい。2007/06/28(木) 18:12:31
UNIXシェルの新刊はここ2年くらいやたら出たが、
もうこの分野で出ても意味ないわな。
カーニハン&パイクとブルース・ブリンけあればいいんじゃないか。
0768名無しさん@お腹いっぱい。2007/06/28(木) 18:17:41
>>766
どこまでの安全性を言ってるのかわからないけど、

(unask 77; > /tmp/hoge$$)

じゃだめかい?

mktempコマンドは、必ずしもあるとは限らないと仮定するべきなのだろうか?
0769名無しさん@お腹いっぱい。2007/06/28(木) 18:21:56
mktemp(1) を勧める文書は「pidは容易に推測できるので危険」とか書いてますよね。
実用上はほとんど問題にならないのでしょうが、気持ち悪いので何か安全な方法があるのかお尋ねしました。
0770名無しさん@お腹いっぱい。2007/06/28(木) 18:31:34
本当に安全でないといけないなら、
mkdirとかでちゃんとロックして、
失敗したら別の名前で試すとかするしかない。
作るディレクトリのパーミッションちゃんとしとけば
推測されてもかゆくもないでしょ。
0771名無しさん@お腹いっぱい。2007/06/28(木) 18:49:36
cat /dev/urandom | od -x
0772名無しさん@お腹いっぱい。2007/06/28(木) 19:09:45
>>771
/dev/urandom はポータブルではないわけで、、
0773名無しさん@お腹いっぱい。2007/06/28(木) 19:10:47
こういう時はお約束だろ



>>771
catが無駄です。
0774名無しさん@お腹いっぱい。2007/06/28(木) 19:45:41
正規表現もそれぞれで実装がまちまちなのに、なにを言ってるのか
0775名無しさん@お腹いっぱい。2007/06/28(木) 19:53:31
そもそも正規表現エンジンが内蔵されてる sh なんかあったっけ?
0776名無しさん@お腹いっぱい。2007/06/28(木) 20:07:27
詳説シェルスクリプトが必要とされているな
0777名無しさん@お腹いっぱい。2007/06/28(木) 20:09:05
なんで正規表現の話が出てきたんだ?
0778名無しさん@お腹いっぱい。2007/06/28(木) 20:13:15
774さんの説明に期待
■ このスレッドは過去ログ倉庫に格納されています