Вычитание числа из переменной в пакетном скрипте

Я новичок в пакетном скриптинге, поэтому, пожалуйста, будьте снисходительны к этому вопросу. Когда я вычитаю 1 из переменной TodayDay, значение не обновляется. Ниже находится строка.

set /a "TodayDay=%TodayDay%-1"

Мой вариант использования - определить, меньше ли сегодняшняя дата, чем переменная lastOpenedDate, я хочу установить для lastOpenedDate вчерашнюю дату.

set lastOpenedDate=2017-12-22
IF %TodayYear%-%TodayMonth%-%TodayDay% LSS %lastOpenedDate% (   
  echo Before Subtraction TodayDay is %TodayDay%
  set /a "TodayDay=%TodayDay%-1"
  echo After Subtraction TodayDay is %TodayDay%
)

Когда я запустил приведенный выше код, вывод:

Before Subtraction TodayDay is 20
After Subtraction TodayDay is 20

Я получил другие значения переменных из приведенного ниже кода.

for /F "skip=1 delims=" %%F in ('
    wmic PATH Win32_LocalTime GET Day^,Month^,Year /FORMAT:TABLE
') do (
    for /F "tokens=1-3" %%L in ("%%F") do (
        set TodayDay=0%%L
        set TodayMonth=0%%M
        set TodayYear=%%N
    )
)
set TodayDay=%TodayDay:~-2%
set TodayMonth=%TodayMonth:~-2%

Что я делаю не так?


person Shashank    schedule 20.12.2017    source источник
comment
В пакетных файлах все переменные являются STRINGS. Он ничего не знает ни о DATES, ни о INT, ни о вставке здесь любого другого типа переменной. Если вам нужно выполнить математику даты, вам нужно изменить дату на юлианскую дату, а затем вычесть из нее. Кажется, я дважды отвечал на этот вопрос за последние две недели. Пожалуйста, выполните поиск в StackOverFlow.   -  person Squashman    schedule 20.12.2017
comment
@ Сквошмен, согласен. Но переменная «TodayDay» имеет значение 20. Когда я пытаюсь вычесть 1 из 20, почему он не возвращает 19?   -  person Shashank    schedule 20.12.2017
comment
В вашем коде слишком много недостатков и предостережений, чтобы их можно было объяснить. Даже ответ, который Магу дал вам ниже, все равно потерпит неудачу. Если вам нужно правильно рассчитать дату, вы можете использовать дату по юлианскому календарю с пакетными файлами или обратиться к Powershell.   -  person Squashman    schedule 20.12.2017
comment
@Squashman, ответ, данный Magoo, работает, как и ожидалось. Спасибо за ваши взгляды на это.   -  person Shashank    schedule 20.12.2017
comment
Ваш код работает только в определенных ситуациях. Смотрите мой комментарий к коду Magoo.   -  person Squashman    schedule 20.12.2017


Ответы (1)


Вам нужно искать SO, используя верхнюю панель для delayed expansion. Это часто задаваемые вопросы № 1.

сдача

  set /a "TodayDay=%TodayDay%-1"
  echo After Subtraction TodayDay is %TodayDay%
)

to

  set /a "TodayDay=%TodayDay%-1"
)
echo After Subtraction TodayDay is %TodayDay%

что будет иметь смысл, как только вы ознакомитесь с delayed expansion.

Теперь следующая проблема, с которой вы столкнетесь (которая не проявит себя до 8-го или 9-го числа месяца), заключается в том, что в пакете начальный 0 означает «восьмеричное», поэтому вам действительно нужно

  set /a "TodayDay=1%TodayDay%-1"
)
set "TodayDay=%TodayDay:~-2"
echo After Subtraction TodayDay is %TodayDay%

который добавляет 100 к номеру дня, добавляя 1 перед номером дня, тогда вам нужно получить последние 2 символа.

person Magoo    schedule 20.12.2017
comment
@Shashank, этот код не будет работать в високосные дни или при вычитании до нового месяца. Если дата 2017-12-01, и вы вычтете 1 из дня, это не даст вам 30, так как это последний день ноября. 1 марта 2020 года вам не дадут 29 за февраль. - person Squashman; 20.12.2017
comment
@ Сквошмен, согласен. В моем случае использования не требуется указывать даты, указанные вами. Для 2017-12-01 я получу 0 как день, и меня это устраивает. В любом случае решение, которым вы поделились, является лучшим. Но для моего случая использования мне подходит вышеуказанное решение. - person Shashank; 20.12.2017