我正在尝试为昨天的日期创建一个环境变量。它必须采用MM/DD/YYYY格式。
对于我目前拥有的代码:
set m=%date:~-7,2%
set /A m -= 1
set DATE_YESTERDAY=%date:~-10,2%/%m%/%date:~-4,4%
echo %DATE_YESTERDAY%
然而,当我用-1而不是"12/03/2019“来抵消昨天的影响时,我得到了"12/3/2019”。因此,忽略了0/0。
保留MM/DD/YYYY格式的任何想法
我见过很多关于这方面的其他问题,但是,都是短小的!
注意-我不想要powershell或VBS脚本。我知道这可以通过简单的批处理来完成。
发布于 2019-12-05 06:57:08
Windows命令处理器cmd.exe
不支持日期计算。默认情况下,Windows上安装的其他脚本解释器,如VBScript或PowerShell支持日期计算和复配发布了使用VBScript或PowerShell的解决方案。
下面是一个纯粹的批处理文件解决方案,用于从当前日期计算昨天的日期,并说明代码。为了更快地处理批处理文件,可以删除带有备注命令rem
的行。
@echo off
setlocal EnableExtensions DisableDelayedExpansion
if "%~1" == "" (
rem Get local date and time in a region independent format.
for /F "tokens=2 delims==." %%I in ('%SystemRoot%\System32\wbem\wmic.exe OS get LocalDateTime /VALUE') do set "LocalDateTime=%%I"
) else (
rem This is for fast testing determining the date of yesterday from any
rem date specified as parameter in format yyyyMMdd on calling this batch
rem file from within a command prompt window. The parameter string is
rem not validated at all as this is just for testing the code below.
set "LocalDateTime=%~1"
)
rem Get day, month and year from the local date/time string (or parameter).
set "Day=%LocalDateTime:~6,2%"
set "Month=%LocalDateTime:~4,2%"
set "Year=%LocalDateTime:~0,4%"
rem Define a variable with today's date in format MM/dd/yyyy.
set "Today=%Month%/%Day%/%Year%"
rem Decrease the day in month by 1 in any case.
rem It is necessary to remove leading 0 for the days 08 and 09 as
rem those two days would be otherwise interpreted as invalid octal
rem numbers and decreased result would be -1 instead of 7 and 8.
rem if "%Day:~0,1%" == "0" set "Day=%Day:~1%"
rem set /A Day-=1
rem Faster is concatenating character 1 with the day string to string
rem representing 101 to 131 and subtract 101 to decrease day by one.
set /A Day=1%Day%-101
rem The yesterday's date is already valid if the day of month is greater 0.
if %Day% GTR 0 goto BuildYesterday
rem Yesterday is in previous month if day is equal (or less than) 0.
rem Therefore decrease the current month by one with same method as
rem described above to decrease correct also the months 08 and 09.
set "Day=31"
set /A Month=1%Month%-101
rem Yesterday is in previous year if month is equal (or less than) 0.
if %Month% GTR 0 goto GetLastDay
set /A Year-=1
set "Month=12" & goto BuildYesterday
:GetLastDay
rem Determine last day of month depending on month.
for %%I in (4 6 9 11) do if %Month% == %%I set "Day=30" & goto BuildYesterday
if not %Month% == 2 goto BuildYesterday
rem Determine if this year is a leap year with 29 days in February.
set /A LeapYearRule1=Year %% 400
set /A LeapYearRule2=Year %% 100
set /A LeapYearRule3=Year %% 4
rem The current year is always a leap year if it can be divided by 400
rem with 0 left over (1600, 2000, 2400, ...). Otherwise if the current
rem year can be divided by 100 with 0 left over, the current year is NOT
rem a leap year (1900, 2100, 2200, 2300, 2500, ...). Otherwise the current
rem year is a leap year if the year can be divided by 4 with 0 left over.
rem Well, for the year range 1901 to 2099 just leap year rule 3 would be
rem enough and just last IF condition would be enough for this year range.
set "Day=28"
if LeapYearRule1 == 0 goto BuildYesterday
if NOT %LeapYearRule2% == 0 if %LeapYearRule3% == 0 set "Day=29"
rem The leading 0 on month and day in month could be removed and so both
rem values are defined again as string with a leading 0 added and next just
rem last two characters are kept to get day and month always with two digits.
:BuildYesterday
set "Day=0%Day%"
set "Day=%Day:~-2%"
set "Month=0%Month%"
set "Month=%Month:~-2%"
rem Define a variable with yesterday's date in format MM/dd/yyyy.
set "Yesterday=%Month%/%Day%/%Year%"
echo Today is: %Today%
echo Yesterday is: %Yesterday%
endlocal
请阅读我在为什么%date%在按计划任务执行的批处理文件中产生不同的结果?上的答案,它详细解释了FOR命令行,使用WMIC以区域无关的格式获取当前日期。
下面是上面没有注释、空行和第一个的代码,如果条件只需要测试代码的话。闰年标识也被优化为仅使用第三条规则,这意味着该代码只在1901年至2099年工作,这应该足够了。
@echo off
setlocal EnableExtensions DisableDelayedExpansion
for /F "tokens=2 delims==." %%I in ('%SystemRoot%\System32\wbem\wmic.exe OS get LocalDateTime /VALUE') do set "LocalDateTime=%%I"
set "Day=%LocalDateTime:~6,2%" & set "Month=%LocalDateTime:~4,2%" & set "Year=%LocalDateTime:~0,4%"
echo Today is: %Month%/%Day%/%Year%
set /A Day=1%Day%-101
if %Day% GTR 0 goto BuildYesterday
set "Day=31"
set /A Month=1%Month%-101
if %Month% GTR 0 goto GetLastDay
set /A Year-=1
set "Month=12" & goto BuildYesterday
:GetLastDay
for %%I in (4 6 9 11) do if %Month% == %%I set "Day=30" & goto BuildYesterday
if not %Month% == 2 goto BuildYesterday
set /A LeapYearRule3=Year %% 4
if %LeapYearRule3% == 0 (set "Day=29") else set "Day=28"
:BuildYesterday
set "Day=0%Day%"
set "Day=%Day:~-2%"
set "Month=0%Month%"
set "Month=%Month:~-2%"
echo Yesterday is: %Month%/%Day%/%Year%
endlocal
要了解所使用的命令及其工作方式,请打开一个命令提示符窗口,在那里执行以下命令,并非常仔细地读取为每个命令显示的所有帮助页。
echo /?
endlocal /?
for /?
goto /?
if /?
rem /?
set /?
setlocal /?
wmic /?
wmic os /?
wmic os get /?
wmic os get localdatetime /?
还请参阅使用Windows批处理文件使用多条命令的单行,以了解用于在单个命令行上指定多个命令的操作符&
的说明。
https://stackoverflow.com/questions/59186488
复制相似问题