特定の時間間隔でいくつかのコマンド/スクリプトを実行する必要があり、そのために2つのオプションがあります。
cron
- jobを設定するsleep
でループを実装します。リソース消費の観点から、どちらがより良いオプションですか、なぜですか? cron
がより良い方法ですか? cronは何らかのトリガーを使用していますか? cronはジョブの確認と開始にどのような手順を使用しますか?
Cronを使用してください。これは、より適切で標準的な方法です。少なくともこれが定期的に実行されるものである場合(1分でパッチを当てただけではありません)。 cron
は、よりクリーンで標準的な方法です。ターミナルから切り離されたシェルを実行するため、これも優れています-偶発的な終了や他のプロセスへの依存に関する問題はありません。
リソースについて:CPU:両方のプロセスがスリープします-スリープするとき、CPUを浪費しません。 cron
は、物事をチェックするために頻繁に起動しますが、とにかくそれを実行します(プロセスではこれ以上ありません)。そして、これは無視できる負荷であり、ほとんどのデーモンは時々目を覚ます。メモリ:このプロセスに関係なくcron
を実行している可能性があるため、オーバーヘッドはまったくありません。ただし、cronはスクリプトが呼び出されたときにのみシェルを起動しますが、スクリプトはメモリにロードされたままです(シェル変数にすべてをロードしない限り、環境でのbashプロセス-数キロバイト)。
全体として、リソースについては問題ではありません。
cron
(またはanacron
)を使用します。
Cronは、物事を一定間隔で実行するように設計されています。それが唯一のことであり、長年に渡ってcronが今日の姿にするために多くの作業が行われてきました。
スクリプトでより優れたスケジューラを作成する可能性はほとんどありません。 cronを使用すると、より効果的に機能し、スクリプトに不要なコードが含まれるのを回避し、コードを簡潔で維持しやすくします。
必要がない場合は、ホイールを再発明しないでください。
cron
とsleep
のパフォーマンスについてはすでに良い答えがいくつかありますが、何らかの機能比較を追加したいと思います。
プロcron
:
プロsleep
:
Cronは何らかのトリガーを使用していますか?
cat /proc/`pidof crond`/stack
を確認しました。数回連続して印刷したので、crond
がhrtimer_nanosleepでスリープしているだけだとわかりました。
>cat /proc/`pidof crond`/stack
[<ffffffff810a0614>] hrtimer_nanosleep+0xc4/0x180
[<ffffffff810a073e>] sys_nanosleep+0x6e/0x80
[<ffffffff8100b072>] system_call_fastpath+0x16/0x1b
[<ffffffffffffffff>] 0xffffffffffffffff
sleep
ユーティリティは同じシステムコールを使用します。
>sleep 100 &
[1] 12761
>cat /proc/12761/stack
[<ffffffff810a0614>] hrtimer_nanosleep+0xc4/0x180
[<ffffffff810a073e>] sys_nanosleep+0x6e/0x80
[<ffffffff8100b072>] system_call_fastpath+0x16/0x1b
[<ffffffffffffffff>] 0xffffffffffffffff
私は両方のユーティリティ(crond
&sleep
)のCPU使用率が低い必要があると想定しています。cron
を模倣する必要がある場合は、sleep
を使用できます。
更新。 crond
の活動を観察することをお勧めします
strace -p `pidof crond`
探している主な違いは、cron
が常に実行されていないことです。 man cron
:
cron then wakes up every minute, examining all stored crontabs, check‐
ing each command to see if it should be run in the current minute.
When executing commands, any output is mailed to the owner of the
crontab (or to the user named in the MAILTO environment variable in the
crontab, if such exists). The children copies of cron running these
processes have their name coerced to uppercase, as will be seen in the
syslog and ps output.
言い換えると、cron
は1分に1回だけ開始され、実行する必要があるかどうかをテストします。一方、スリープアプローチでは、実際のsleep
コマンド、シェル、ターミナル、およびwhile
(またはその他の)ループを同時に実行する必要があります。
同じ数のプロセスを起動している場合でも、cron
の方が適しています。それは彼らの仕事がとても上手である傾向がある人々によってこれのために正確に書かれています。単純なシェルループよりもうまく機能するはずです。
違いは、スリープする必要があるスクリプトを追加すると、スケジュールされたスクリプトを起動して実行する次の実行まで閉じる単一のプロセス(cron)ではなく、多くのプロセスが待機してスリープ状態になることです。 Cronでは、他のスクリプトを時間どおりに実行することに特化した1つのプロセスを使用できます。さらに、cronを使用すると、何かを実行する必要があるとき、曜日または月、特定の時間、または5分ごとなど、比較的自由にスケジュールできます。
*これをもう一度見ただけで、cronのもう1つの利点を思いつきました。定期的に実行されるすべてのスクリプトは1か所にあり、そこから、いつどのくらいの頻度で実行されるかを簡単に確認できます。それ以外の場合は、個々のスクリプトを確認する必要があります。
すでに十分な情報に基づいた適切な回答がありますが、sleep
を使用すると、たとえば他のいくつかの変数の関数として、プロセスをさまざまな時間フリーズすることができることを指摘したいと思います。
バッテリーの残量を確認するスクリプトを記述している場合、notify-send
が事前定義のクリティカルレベルを下回っている場合は、スクリプトをsleep
にして、次の関数を実行できます。最後にチェックしたときに80%であることがわかっている場合でも、cronを使用して1〜2分ごとにバッテリーをチェックするのではなく、現在のバッテリーレベルをパーセンテージで表示します。
Battery_notify.sh
#!/bin/bash
CRIT=15
while true; do
# current battery level
BAT_LEVEL=`acpi -b |grep -Eo "[0-9]+%"|grep -Eo "[0-9]+"`
interval=$((($BAT_LEVEL -$CRIT) * 120)) # loose estimate of backup time for each percentage of battery charge.
# Is AC plugged in?
state=`acpi -b |grep -Eo "[A-Za-z]+harging"`
#only notify if not Plugged in
if [ "$state" = "Discharging" ] ; then
# is battery below CRIT level?
if [ $BAT_LEVEL -le $CRIT ]; then
aplay ~/apert.wav &
notify-send "Battery-Low!!!" -i /home/bibek/batt.png -t 900
sleep 100 # nag me each 100 secs untill I plug the thing
else
sleep $interval
fi
else
# if plugged in sleep
if [ $BAT_LEVEL -le $CRIT ]; then
sleep $interval
else
# to check if the AC is unplugged before battery gains charge above CRIT.
sleep 100
fi
fi
done
単一のジョブに対してsleep
の代わりにcron
を使用する方が効率的かもしれません。ただし、通常はcron
を実行しているので、それを使用しても無料で利用できます。ですから、そうでなければcron
- free組み込みシステムを使用しているのでなければ、cron
を選びます。