以下のサブルーチンは2つの部分で構成されています。まず、最初のパラメータで指定された日付をチェックし、日付が不良の場合はERRORLEVEL=1を返します。必要に応じて、年の有効範囲を挿入できます(そうでない場合は、yyOKパーツを削除します)。
次に、基本時間とタイムゾーンを2番目と3番目のパラメーターで調整し、調整された日付を表示します。
:validateDate result= YYYY/MM/DD [HH HHAdjust]
setlocal EnableDelayedExpansion
set i=0
for %%a in (31 28 31 30 31 30 31 31 30 31 30 31) do (
set /A i+=1
set daysPerMonth[!i!]=%%a
)
set result=Invalid date
for /F "tokens=1-3 delims=/" %%a in ("%2") do set yy=%%a& set mm=%%b& set dd=%%c
set /A yy=%yy%, mm=10%mm% %% 100, dd=10%dd% %% 100, yyMOD4=yy%%4 >NUL 2>&1 || goto exit
if %yyMOD4% equ 0 set daysPerMonth[2]=29
set /A yyOK=0, mmOK=0, ddOK=0
rem Modify year limits as you wish (or remove they):
if %yy% geq 1900 if %yy% leq 2015 set yyOK=1
if %mm% geq 1 if %mm% leq 12 set mmOK=1
id %dd% geq 1 if %dd% leq !daysPerMonth[%mm%]! set ddOK=1
set /A dateOK=yyOK*mmOK*ddOK
if %dateOK% neq 1 goto exit
rem Date is correct
set result=%yy%/%mm%/%dd%
rem Adjust the hour to different time zone, if given
rem %3=base hour, %4=adjust with sign (+ or -)
if "%4" equ "" goto exit
set /A newHH=10%3 %% 100 %4
if %newHH% gtr 23 (
rem Pass to next day
set /A newHH-=24, dd+=1
if !dd! gtr !daysPerMonth[%mm%]! (
set /A dd=1, mm+=1
if !mm! gtr 12 (
set /A mm=1, yy+=1
)
)
)
if %newHH% lss 1 (
rem Pass to previous day
set /A newHH+=24, dd-=1
if !dd! lss 1 (
set /A mm-=1
if !mm! lss 1 (
set /A mm=12, yy-=1
)
for %%m in (!mm!) do (
set /A dd=daysPerMonth[%%m]
)
)
)
set result=%yy%/%mm%/%dd% %newHH%
:exit
endlocal & set %1=%result%
exit /B
このプログラムをテストし、問題があれば報告してください。
編集:新しいOPの要件に合うように以前のプログラムを変更しました。
サブルーチンは、結果とともにERRORLEVEL値を返さなくなりました。結果を受け取る変数を示す新しい最初のパラメーターを使用して呼び出す必要があります。元の日付が不良の場合は「無効な日付」になります。基準時間と調整時間が指定されている場合、戻り値には調整された日付と時間が含まれます。例えば:
call validate.bat adjusted= 2012/3/5 3 -2
if "%adjusted%" neq "Invalid date" (
echo Adjusted date and hour are: %adjusted%
)
アントニオ