トップページunix
1001コメント312KB

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

■ このスレッドは過去ログ倉庫に格納されています
0001うはwwwww2006/03/26(日) 00:56:22
シェルスクリプトの総合スレです。
スクリプトのお勉強・自慢・腕試しなどにどうぞ。
まずは注意点、リンク、地鎮祭など(>>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 でトレースしましょう。
0002おkwwwwwwwwwwwww2006/03/26(日) 00:57:10
□前スレや過去スレ:
シェルスクリプト総合 その5
http://pc8.2ch.net/test/read.cgi/unix/1137801629/
シェルスクリプト総合 その4
http://pc8.2ch.net/test/read.cgi/unix/1131026501/
シェルスクリプト総合 その3
http://pc8.2ch.net/test/read.cgi/unix/1124889646/
シェルスクリプト総合 その2
http://pc8.2ch.net/test/read.cgi/unix/1113664637/
シェルスクリプト総合 その1
http://pc8.2ch.net/test/read.cgi/unix/1101820646/

□関連スレ:
sed
http://pc8.2ch.net/test/read.cgi/unix/1085730992/
正規表現
http://pc8.2ch.net/test/read.cgi/unix/1039165754/
おまえら! shell は何を使っているんですか?
http://pc8.2ch.net/test/read.cgi/unix/1012330865/
Eshell の使い方とか設定とか【Emacs Shell、Lisp】
http://pc8.2ch.net/test/read.cgi/unix/1102921590/

□他板の関連スレ:
【sed】シェルスクリプト総合@LINUX【awk】
http://pc8.2ch.net/test/read.cgi/linux/1121994321/
【Shell】どのシェル使ってる?【Script】
http://pc8.2ch.net/test/read.cgi/linux/1067330754/
0003ちょwwwwww2006/03/26(日) 00:58:49
□初心者向けリンク
「誰にでも」シリーズ
ttp://kanji.zinbun.kyoto-u.ac.jp/~yasuoka/publications/dareUni/
/bin/shプログラミング入門
ttp://freebooks.info.nara-k.ac.jp/archive/ShellProgramming/
シェルを使おう - 導入からプログラミングまで -
ttp://www.netfort.gr.jp/~tomokuni/lms/shell/text/

□入門者向け書籍:
プロフェショナルシェルプログラミング
http://www.amazon.co.jp/exec/obidos/ASIN/4756116329/
入門UNIXシェルプログラミング―シェルの基礎から学ぶUNIXの世界
http://www.amazon.co.jp/exec/obidos/ASIN/4797321946/
UNIXシェルプログラミング徹底解説
http://www.amazon.co.jp/exec/obidos/ASIN/4822280489/
入門Kornシェル
http://www.amazon.co.jp/exec/obidos/ASIN/4873110149/
入門bash
http://www.amazon.co.jp/exec/obidos/ASIN/4900900788/

□参考リンク:
UNIXの部屋 (沢山のコマンドの簡単な紹介など)
http://x68000.q-e-d.net/~68user/unix/
POSIX: Shell & Utilities (標準規格)
http://www.opengroup.org/onlinepubs/009695399/utilities/contents.html
0004ワッフルワッフル2006/03/26(日) 01:00:22
□関連書籍と関連リンク:
FreeBSD Hypertext Man Pages
http://www.freebsd.org/cgi/man.cgi
Linux JF (Japanese FAQ) Project.
http://www.linux.or.jp/JF/
Unix Programming Frequently Asked Questions 日本語訳
http://www.adl.nii.ac.jp/~moro/unix-programmer/faq-j_toc.html
UNIXプログラミング環境
http://www.amazon.co.jp/exec/obidos/ASIN/4871483517/

□人間初心者へのお願い:
・このスレはシェルスクリプトについてのスレです。
 シェルの対話的な利用についての話やスクリプトと関係ないコマンドの
 使い方の質問などはスレ違いなので無用に願います。

□シェルスクリプトでよく使うコマンド:
制御・条件判定系: [,test,expr,true,false,yes,getopts

テキスト処理系: cat,awk,sed,tr,sort,uniq,grep,wc,head,tail,cut,paste,comm,join

ファイル検索系: find,xargs
(スペースなどを含むファイル名を正しく処理するため、
findは -print0、xargsは -0オプションを常に付けることを推奨
ただし、Solarisでは未対応。どうするんだろ?)

ディレクトリ系: basename,dirname
出力系: echo,printf
対話コマンド制御系: expect
http/ftpの処理自動化: wget,curl
0005名無しさん@お腹いっぱい。2006/03/26(日) 01:00:52
□最近のシェルスクリプト本(1)

(2004/03) UNIXシェルスクリプトハンドブック 関根 達夫 (著)
http://amazon.co.jp/o/ASIN/4797326522/

(2004/10) UNIXシェルスクリプト逆引き大全333の極意 中橋 一朗 (著)
http://amazon.co.jp/o/ASIN/4798008842/

(2004/11) 仕事に使えるLinuxシェルスクリプト 千葉 真人 (著)
http://amazon.co.jp/o/ASIN/4822282090/

(2004/12) UNIXシェルスクリプトサンプルブック デイブ・テイラー (著)
http://amazon.co.jp/o/ASIN/4797327286/

(2005/02) シェルスクリプト基本リファレンス 山森 丈範 (著)
http://amazon.co.jp/o/ASIN/4774122610/

(2005/04) LinuxWorldスクリプト 月刊リナックス・ワールド総集編 月刊LinuxWorld特別 (著)
http://amazon.co.jp/o/ASIN/4872802349/

(2005/05) UNIXシェルスクリプトコマンドブック 山下 哲典 (著)
http://amazon.co.jp/o/ASIN/4797330635/

(2005/05) わかる&使える UNIX基礎講座 シェルスクリプト編 中井 獏 (著)
http://amazon.co.jp/o/ASIN/4774123625/
0006名無しさん@お腹いっぱい。2006/03/26(日) 01:02:35
□最近のシェルスクリプト本(2)

(2005/07) UNIX シェルスクリプト辞典 川井 義治 (著),志田 智 (著),田淵 貴昭,米田 聡
http://amazon.co.jp/o/ASIN/4798109231/

(2005/08) シェルスクリプト ポケットリファレンス bash編 宮原 徹 (著), 川原 龍人 (著)
http://www.amazon.co.jp/o/ASIN/4774124818/

(2005/12) 図解でわかるLinuxシェルスクリプト・正規表現 小泉 修(著)
http://www.amazon.co.jp/o/ASIN/4534040067/

(2006/01) 詳解 シェルスクリプト アーノルド ロビンス (著), ほか
http://www.amazon.co.jp/o/ASIN/4873112672/
0007名無しさん@お腹いっぱい。2006/03/26(日) 01:03:05
以上でーす。
0008名無しさん@お腹いっぱい。2006/03/26(日) 01:16:47
|乙>>1|
       //
>三三三 //    ∧_∧ //
( ´>`)y=-※==(・Д・※==================⊃
(    ○      (     )
| ||    // /
(_)_)     (_(_)
0009名無しさん@お腹いっぱい。2006/03/26(日) 01:39:52
>>1
乙。
0010名無しさん@お腹いっぱい。2006/03/26(日) 10:34:22
rm -rf *
0011名無しさん@お腹いっぱい。2006/03/26(日) 14:57:07
結論。シェルを書いて、UNIXを打て!
0012名無しさん@お腹いっぱい。2006/03/27(月) 14:50:04
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0013名無しさん@お腹いっぱい。2006/03/27(月) 16:21:08
前スレで紹介されてた debianの checkbashismsというコマンド、
perlスクリプトだったので持ってきて、いろいろ試してみた。

手元にあった bashスクリプトの1行目を #!/bin/sh に書き換えて
checkbashismsにかけてみたけど・・・
・・・なんかチェック甘いね。
ほとんど何も引っかからない。
引っかかったのは ${HOGE//hage/boke} くらい。

引っかけて欲しかった、↓は、
for ((i = 0; i < 10; i++)) { echo $i; }
通ってしまった。

これってbash依存じゃないの?
0014名無しさん@お腹いっぱい。2006/03/27(月) 16:37:07
>>13
@bashism_regexs にあるのしかひっかけないみたいね。
パッケージ作る際にありがちなのだけひっかかれば十分、
っていう考えなんじゃないの?
0015名無しさん@お腹いっぱい。2006/03/27(月) 17:14:55
perlって時点で真面目な作りを期待するのは無理があるね。

bashのソースを改造して、構文解析でbash依存の構文が出現したら
メッセージを出すようにすれば簡単に作れると思うんだけど。
0016名無しさん@お腹いっぱい。2006/03/27(月) 23:24:20
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0017HelpME2006/03/28(火) 14:20:36
シェルスクリプト勉強中のものです。
tcshで困ってます。

----------------------------------------
#!/bin/sh

MYPATH=`pwd`
---------------------------------------
はOKなのに

------------------------------------------
#!/bin/tcsh

MYPATH=`pwd`
------------------------------------------
はNGなのは何故なんでしょう。

shとtcshでは変数に値を入れる文法って
違うのでしょうか?
0018名無しさん@お腹いっぱい。2006/03/28(火) 14:25:26
tcsh のことは忘れてよい。
0019名無しさん@お腹いっぱい。2006/03/28(火) 15:10:52
>>17
>>1 嫁。
>・csh/tcshのシェルスクリプトは推奨されません。
> (理由は「csh-whynot」でググれ)
0020名無しさん@お腹いっぱい。2006/03/28(火) 15:16:38
忘れてよい以前に17はtcshのことなんて全然知らんがな
0021名無しさん@お腹いっぱい。2006/03/28(火) 15:27:06
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0022名無しさん@お腹いっぱい。2006/03/28(火) 15:30:35
良スレの予感
0023csh大好きっ子2006/03/28(火) 18:53:30
>>17
set MANPATH = `pwd`
0024名無しさん@お腹いっぱい。2006/03/28(火) 20:19:40
>>23
ばかもん。答えるなよ。皆んな知ってても敢えて答えなかったのに。
0025名無しさん@お腹いっぱい。2006/03/28(火) 21:00:47
削除依頼出して来るわ。
0026名無しさん@お腹いっぱい。2006/03/28(火) 21:33:14
基本的なことかも知れませんが、
シェルとUNIXとで実行結果が異なる場合、
どういった原因が考えられますか?
0027名無しさん@お腹いっぱい。2006/03/28(火) 21:51:02
>>26
キミの日本語インタープリターが壊れている。
0028名無しさん@お腹いっぱい。2006/03/28(火) 22:05:10
>>26
それは多分UNIXが間違ってるんだろうね。
ちゃんと手を洗ってからインストールした?
ウイルス入っちゃってるかもよ。
0029名無しさん@お腹いっぱい。2006/03/28(火) 22:33:07
あるコマンドを2回だけ繰り返し実行したいのです。
たった2回なのでforやwhileにするのは大げさなので、

#!/bin/sh
あるコマンド
!!

というシェルを書きましたが、エラーになります。
UNIXだと

$ あるコマンド
$ !!

で実行できます。なぜこうなるのでしょう?
0030名無しさん@お腹いっぱい。2006/03/28(火) 22:44:42
あるコマンド.exe にパスが通ってないんじゃないか?
0031名無しさん@お腹いっぱい。2006/03/28(火) 22:49:02
>>29
あんたは「シェル」を書いたんじゃなくて「シェルスクリプト」を書いた。
「UNIXだと」じゃなくて「シェルプロンプトだと」だ。
おそらくあんたの使っているシェルは/bin/bashか/bin/ksh。これらは/bin/shと違って !! で直前のコマンドを実行できる。

絶対確実というわけではないけど、どのシェルを使っているかは、

echo $SHELL

を実行してごらん。
0032名無しさん@お腹いっぱい。2006/03/28(火) 22:54:44
>>31
$ echo $SHELL
/bin/sh

と出ましたが。
0033名無しさん@お腹いっぱい。2006/03/28(火) 23:04:09
>>31
kshで!!が使えるとは、初耳です。
0034名無しさん@お腹いっぱい。2006/03/28(火) 23:22:23
!で始まるヒストリ操作はcsh由来だからcsh否定論者は使えないなww
0035名無しさん@お腹いっぱい。2006/03/28(火) 23:27:11
UNIX打つの人来てたのかー
0036312006/03/28(火) 23:36:41
>>33
すまん、間違えた。

>>32
うーむ、今動いてるシェルが何かを確実に見極める方法は知らない。
bashを使っているという前提で次の事を試してみて。

Tabキーを連続して2回押すとどう表示されるか?

echo $BASH  の出力は?

ps の出力は?
0037名無しさん@お腹いっぱい。2006/03/28(火) 23:37:16
あるコマンド
あるコマンド

と素直に二行書けばいいじゃん
0038Masa ◆Masa.mmzoo 2006/03/28(火) 23:45:03
sync
sync
sync
0039名無しさん@お腹いっぱい。2006/03/29(水) 00:13:31
>>29
起動する時に-funroll-loopsオプションをつけると
自動的に展開される
0040名無しさん@お腹いっぱい。2006/03/29(水) 00:57:52
!!
!-5
!32
!!
0041名無しさん@お腹いっぱい。2006/03/29(水) 00:59:14
>>37 無能
0042名無しさん@お腹いっぱい。2006/03/29(水) 02:24:03
質問です

aaa.txtという名前の2000バイト固定長ファイルの500〜502バイト目が
'xyz'のときだけ、そのレコードをbbb.txtにコピーするためには
どのようなスクリプトを作ればよろしいのでしょうか?

よろしくお願いします。
0043名無しさん@お腹いっぱい。2006/03/29(水) 02:49:01
> aaa.txtという名前の2000バイト固定長ファイル

固定長なのはレコード長なのじゃないのか?

#!/bin/sh
infile=aaa.txt; outfile=bbb.txt; tmpfile=/tmp/foo.$$
echo 'xyz\c' > $tmpfile.1
dd bs=1 skip=500 count=3 < $infile > $tmpfile.2
if cmp $tmpfile.1 $tmpfile.2; then
cp $tmpfile.2 $outfile
fi
rm $tmpfile.1 $tmpfile.2
0044名無しさん@お腹いっぱい。2006/03/29(水) 05:30:09
head -c502 aaa.txt | tail -c3
とかでいけそうな気もする
0045名無しさん@お腹いっぱい。2006/03/29(水) 06:46:49
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0046名無しさん@お腹いっぱい。2006/03/29(水) 10:03:33
>>29
2回だけ手軽に繰り返したい、という質問なら、

#!/bin/sh
a='あるコマンド'
$a
$a


コマンドラインで !! が実行できるのに、
シェルスクリプト中では実行できないのは何故かという質問なら、

それは、「インタラクティブかどうか」でシェル自身が動作を変えているから。

!! が使える bashや zshであっても、
シェルスクリプト中では !!はただの !!という文字列になる。
0047名無しさん@お腹いっぱい。2006/03/29(水) 11:10:39
なんで >>37 じゃだめなん?
0048名無しさん@お腹いっぱい。2006/03/29(水) 11:43:34
tcshなら
repeat 2 あるコマンド
0049名無しさん@お腹いっぱい。2006/03/29(水) 12:13:07
>>48
それだと「構文」になっちゃうから、「手軽」にならない。
しかも、(t)cshの文法はタブー。

「構文」使ってもいいなら↓
for i in 1 2; do あるコマンド; done
0050名無しさん@お腹いっぱい。2006/03/29(水) 12:16:05
cshだと、スクリプトの中でさえ !!が使えるぞ。

#!/bin/csh
あるコマンド
!!

で桶。
なんたる糞Cシェル。

副作用として、
echo 'Hello !!'
が、シングルクォートで囲んでいるのに !!が展開されてしまう。
なんたる糞Cシェル。
0051名無しさん@お腹いっぱい。2006/03/29(水) 12:36:44
>>50
解ってるなら
不利益になるコマンドは使わなければ良いんだろ
0052名無しさん@お腹いっぱい。2006/03/29(水) 15:02:37
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0053名無しさん@お腹いっぱい。2006/03/29(水) 15:13:43
>>52
飽きた
0054名無しさん@お腹いっぱい。2006/03/29(水) 16:01:48
sed と awk はどちらの方が実行速度で有利ですか?
0055名無しさん@お腹いっぱい。2006/03/29(水) 16:08:20
計ってみれば?
0056名無しさん@お腹いっぱい。2006/03/29(水) 16:08:34
>>54
んなもんやることによって違うに決まってるでしょ
0057名無しさん@お腹いっぱい。2006/03/29(水) 16:09:09
>>54
もちろん sed。(sedで書けるものはなるべくsedで)
0058名無しさん@お腹いっぱい。2006/03/29(水) 16:41:08
ありがとうござます。
バイナリサイズは sed < awk で4倍も差があったので、基本は sed で、
sed ではすっきりしないAVアホですっきりしたい時は awk って事にします。
0059名無しさん@お腹いっぱい。2006/03/29(水) 17:44:30
>>58
バイナリサイズの時間への影響なんて誤差の範囲だし、
メモリに載ってるかどうかで逆転する。つまり気にする意味がない。

速度が気になるなら57を鵜飲みにせず自分で2通り書いてはかってみれ。
0060名無しさん@お腹いっぱい。2006/03/29(水) 18:24:45
sed 's/hoge/hage/g'
と、
awk '{ gsub(/hoge/, "hage"); print }'
とで比較すると、

sedの方が約2倍速いなぁ。


>>59
「バイナリサイズの時間への影響はメモリに載ってるかどうかで逆転する」
というのは同意だが、それはsed/awkの起動時のオーバーヘッドであって、
起動中の文字列処理速度とは別の話。

sedでもできる処理をawkにやらせると、やっぱりawkの方が遅くなるよ。
0061名無しさん@お腹いっぱい。2006/03/29(水) 18:27:21
sed 使うか awk 使うか迷う場面ってどんなんだ?
0062名無しさん@お腹いっぱい。2006/03/29(水) 18:28:21
sed/awkについてはスレ違い。

sedは↓
http://pc8.2ch.net/test/read.cgi/unix/1085730992/l50

awkはスレがないけど、必要なら誰か立てて。
0063名無しさん@お腹いっぱい。2006/03/29(水) 18:32:49
awkについて語るスレ
http://pc8.2ch.net/test/read.cgi/tech/1023556171/

でも比較の話は中立な所でするほうが良いような。
0064名無しさん@お腹いっぱい。2006/03/29(水) 19:19:34
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0065名無しさん@お腹いっぱい。2006/03/30(木) 00:53:43
>64
なにいってんだハゲ
帰れ
0066名無しさん@お腹いっぱい。2006/03/30(木) 01:53:10
なぁ





                        お願いだから糞スレを立てないでくれるかな?



           俺からのお願いだよ


                               分かったら削除依頼よろしく
0067名無しさん@お腹いっぱい。2006/03/30(木) 02:29:52
>>65
これスクリプトで書き込んでいるんじゃないのか?w
0068名無しさん@お腹いっぱい。2006/03/30(木) 08:42:51
結果が多少異なる点は放置して、こうなりました。

>find / -print > find.txt
>ls -l find.txt
-rw-r--r-- 1 root whell 27679632 Mar 30 07:39 find.txt
>time awk -F / '{print $1"/"$2"/"$3}' < find.txt >> /dev/null
17.871u 0.569s 0:18.57 99.2% 148+277k 0+0io 0pf+0w
>time sed -ne 's|^\([^/]*/[^/]*/*[^/]*\).*|\1|p' < find.txt >> /dev/null
770.721u 4.670s 13:00.62 99.3% 35+235k 0+0io 0pf+0w
>time sed -ne 's|^\([^/]*\)/*\([^/]*\)/*\([^/]*\).*|\1/\2/\3|p' < find.txt >>/dev/null
1616.450u 8.887s 27:16.78 99.3% 35+235k 0+0io 0pf+0w

sedに問題がありそうですが、そこはsedスレに行きましょう。
■ このスレッドは過去ログ倉庫に格納されています