日付を指定すると、土日、祝祭日(国民の祝日)かどうかをチェックするサブルーチンです。
このサブルーチンは、土日と、日本における「国民の祝日」とが対象です。海外の祝祭日や、あなたの会社の設立記念日など、あなたが休みだとしても、それは対象となりませんので注意してください。祝祭日(国民の祝日)は、内閣府のホームページ http://www8.cao.go.jp/chosei/shukujitsu/gaiyou.html で公開されています。このサブルーチンは、2002 年 3 月 25 日時点で内閣府のホームページで公開されていた情報を元に作成されています。もし、国民の祝日が改定された場合にはご注意ください。平成 15 年 1 月 1 日実施予定の「海の日」「敬老の日」の改正には対応しております。
■ サブルーチン名
CheckHoliday
■ 引数
休日かどうかをチェックしたい日付を西暦、月、日に分けて指定します。
- 西暦(1970 〜 2023)
- 月(1 〜 12)
- 日(1 〜 31)
■ 戻値
指定日が土日もしくは祝祭日であれば「1」が、そうでなければ「0」が返ります。また不適切な引数を与えると、-1 が返ります。
■ 使い方
まず、このサブルーチンを使うスクリプトのはじめのほうに、
use Time::Local; を記述してください。お使いのサーバに、Perl モジュール Time がインストールされていないと、このサブルーチンはご利用いただけませんので、ご注意さい。Perl モジュール Time は、Perl5 の標準モジュールですので、ほとんどのサーバでご利用いただけるはずです。
さて、西暦 2002 年 3 月 21 日という日付を評価する場合には、
$year = 2002;
$month = 3;
$day = 21;
$holiday = &CheckHoliday($year, $month, $day);とします。西暦 2002 年 3 月 21 日は春分の日で祝日なので、$holiday には 1 が与えられます。もし、なんでもない日(平日)を指定すると、$horiday には 0 が与えられます。使い方としては、以下のように if 文や unless 文の評価式で使うのがよろしいかと思います。
if(&CheckHoliday($year, $month, $day)) {
#休日の場合の処理
} else {
#平日の場合の処理
}【注意事項】
内閣府が公開している「国民の祝日」には、「春分日」及び「秋分日」については、国立天文台が、毎年2月に翌年の「春分日」、「秋分日」(暦要項)を官報で公表しています。 と書かれています。つまり、日が確定しているものではありません。このサブルーチンは「春分の日」を 3 月 21 日、「秋分の日」を 9 月 23 日と定義しております。少なくとも 2003 年まではこれで問題ありません。将来、もし、天文台がこれらの日を変更した場合には、このサブルーチンの定義を変更する必要がありますので、ご注意ください。
■ サブルーチン
sub CheckHoliday {
my($year, $mon, $day) = @_;
my $time;
eval {$time = timelocal(0, 0, 0, $day, $mon-1, $year-1900);};
if($@) {return -1;}
#当日を特定する。
my @list = localtime($time);
my $today = sprintf("%02d", $mon).sprintf("%02d", $day);
my $youbi = $list[6];
my $order = int(($day-1) / 7) + 1;
#前日を特定する。
my @y_list = localtime($time-60*60*24);
my $yesterday = sprintf("%02d", $y_list[4]+1).sprintf("%02d", $y_list[3]);
my $y_youbi = $y_list[6];
my $y_order = int(($y_list[3] - 1) / 7) + 1;
my $y_flag = 0;
#翌日を特定する
my @t_list = localtime($time+60*60*24);
my $tomorrow = sprintf("%02d", $t_list[4]+1).sprintf("%02d", $t_list[3]);
my $t_youbi = $t_list[6];
my $t_order = int(($t_list[3] - 1) / 7) + 1;
my $t_flag = 0;
#当日が日曜日かどうかをチェック
if($youbi == 0) {return 1;}
#当日が土曜日かどうかをチェック
if($youbi == 6) {return 1;}
#日付が決まっている祝日を定義
my @fix_horidays;
if($year <= 2002) {
@fix_horidays = ('0101', '0211', '0321', '0429', '0503', '0505',
'0720', '0915', '0923', '1103', '1123', '1223');
} else {
@fix_horidays = ('0101', '0211', '0321', '0429', '0503', '0505',
'0923', '1103', '1123', '1223');
}
#当日が固定休日かどうかをチェック
if(grep(/^$today$/, @fix_horidays)) {return 1;}
#当日が変動休日かどうかをチェック
# 成人の日 1月の第2月曜日
# 体育の日 10月の第2月曜日
# 2003年以降は、加えて、
# 海 の 日 7月の第3月曜日
# 敬老の日 9月の第3月曜日
if($mon eq '1' && $youbi == 1 && $order == 2) {return 1;}
if($mon eq '10' && $youbi == 1 && $order == 2) {return 1;}
if($year >= 2003) {
if($mon eq '7' && $youbi == 1 && $order == 3) {return 1;}
if($mon eq '9' && $youbi == 1 && $order == 3) {return 1;}
}
#昨日が固定休日かどうかをチェック
if(grep(/^$yesterday$/, @fix_horidays)) {$y_flag = 1;}
#昨日が変動休日かどうかをチェック
my $y_mon = substr($yesterday, 0, 2);
if($y_mon eq '1' && $y_youbi == 1 && $y_order == 2) {$y_flag = 1;}
if($y_mon eq '10' && $y_youbi == 1 && $y_order == 2) {$y_flag = 1;}
if($year >= 2003) {
if($y_mon eq '7' && $y_youbi == 1 && $y_order == 3) {$y_flag = 1;}
if($y_mon eq '9' && $y_youbi == 1 && $y_order == 3) {$y_flag = 1;}
}
#昨日が休日で、かつ昨日が日曜日の場合には、当日は休日
if($y_flag == 1 && $y_youbi == 0) {return 1;}
#明日が固定休日かどうかをチェック
if(grep(/^$tomorrow$/, @fix_horidays)) {$t_flag = 1;}
#明日が変動休日かどうかをチェック
my $t_mon = substr($tomorrow, 0, 2);
if($t_mon eq '1' && $t_youbi == 1 && $t_order == 2) {$t_flag = 1;}
if($t_mon eq '10' && $t_youbi == 1 && $t_order == 2) {$t_flag = 1;}
if($year >= 2003) {
if($t_mon eq '7' && $t_youbi == 1 && $t_order == 3) {$t_flag = 1;}
if($t_mon eq '9' && $t_youbi == 1 && $t_order == 3) {$t_flag = 1;}
}
#昨日と明日がともに祝日の場合には、当日は休日。
if($y_flag && $t_flag) {return 1;}
#以上のチェックにひっかからなかったら、休日でない。
return 0;
}
|