延迟环境变量扩展
最后重写批处理代码,以避免由于在IF
块并在同一个块中对其进行评估,就像您在
if %oldpass%==%password% (
attrib -h -s "password.txt"
attrib -h -s "tipp.txt"
cls
echo.
echo Enter new password.
set/p newpass= ">"
echo( %newpass% > password.txt
)
rem ...
)
命令行解释器cmd.exe
替换所有%env%
within (
... )
在评估之前按其值进行阻止IF
条件导致例如newpass
总是什么都不是(最有可能)。在命令提示符窗口中阅读命令的完整帮助set
输入后输出help set
or set /?
有关延迟扩展的详细信息。
打字错误
有{
代替(
在您问题的上述代码块中。
块压痕
您应该在 a 内缩进行(
... )
块,否则任何人都很难看到块结构,这使得代码检查非常困难。
RETURN 时环境变量不变
如果用户必须输入分配给环境变量的字符串,则用户始终可以只按 RETURN 或 ENTER 键,而无需输入任何内容。在这种情况下,如果环境变量已经存在,则环境变量的值根本不会改变。因此建议使用前确保环境变量不存在set /p
如果用户必须输入一些内容。
另一种可能性是为环境变量分配了默认值,因此如果应使用默认值,用户只需按 RETURN 或 ENTER。但在此批处理代码中,用户应始终输入所有字符串。
分配给环境变量的尾随空格
可以将带有空格的字符串分配给环境变量,并且空格也可以位于字符串的末尾。批处理文件中的尾随空格是批处理文件无法按预期工作的常见原因。解决方案是使用 set“var=value”,因为在这种情况下,命令执行时会忽略第二个双引号后面的尾随空格。
字符串始终与周围的双引号进行比较
环境变量与字符串值的比较应始终在环境变量引用和字符串值周围使用双引号进行。否则,当用户输入任何内容时,很容易发生这种情况IF
条件被解析为
if ==new goto newpass
这是无效的并且cmd.exe
中断批处理文件的执行。这不会再发生了
if /i "%pass%"=="new" goto NEWPASS
/i
使比较不区分大小写。
用户输入的双引号会破坏批处理脚本
但是用户仍然可以通过现在输入双引号字符来中断批处理文件的执行。解决方案是在进行字符串比较之前从输入的字符串中删除所有双引号,例如使用
set newpass=%newpass:"=%
但这会导致另一个问题,如果newpass
在提示用户输入新密码并且用户不输入任何内容之前删除。这将再次导致无效的命令行语法cmd.exe
。解决方案是预先定义newpass
and passtipp
只用"
作为价值。现在用户可以按 RETURN 键,但变量仍然存在"
作为价值。接下来将删除此双引号,并且批处理代码在下一行检测到用户尚未输入任何内容,否则单个双引号将被不同的内容替换。
最终批次代码
@echo off
title Folder Locker by KBKOZLEV
:SETPASS
set "tipp="
set "password="
if exist "password.txt" (
set /p password=<password.txt
attrib +h +s "password.txt"
)
if exist "tipp.txt" (
set /p tipp=<tipp.txt
attrib +h +s "tipp.txt"
)
:START
if exist "Locked" goto OPEN
if exist "Unlocked" goto LOCK
if not exist "Unlocked" goto MDLOCKER
:LOCK
ren "Unlocked" "Locked"
attrib +h +s "Locked"
echo.
echo Folder locked.
CHOICE /C X /T 5 /D X > nul
exit
:MDLOCKER
md "Unlocked"
echo>password.txt 1234
echo>tipp.txt 1234
attrib +h +s "password.txt"
attrib +h +s "tipp.txt"
cls
echo.
echo Private folder created successfully.
CHOICE /C X /T 5 /D X > nul
goto END
:OPEN
cls
echo.
echo Password tipp: %tipp%
echo.
echo Enter password to unlock folder or
echo enter "new" to set a new password.
echo.
set "pass="
set /p "pass=Password: "
if /i "%pass%"=="new" goto NEWPASS
if "%pass%"=="%password%" (
attrib -h -s "Locked"
ren "Locked" "Unlocked"
echo.
echo Folder unlocked successfully.
goto END
)
goto FAIL
:FAIL
cls
echo.
echo Invalid password, please try again.
CHOICE /C X /T 5 /D X > nul
cls
goto OPEN
:NEWPASS
cls
echo.
set "oldpass="
set /p "oldpass=Old password: "
if not "%oldpass%"=="%password%" goto FAIL
:ENTERNEW
cls
echo.
set "newpass=""
set /p "newpass=New password: "
set newpass=%newpass:"=%
if "%newpass%"=="" (
echo.
echo Invalid new password, please enter new password again.
CHOICE /C X /T 5 /D X > nul
goto ENTERNEW
)
if exist "password.txt" attrib -h -s "password.txt"
echo>password.txt %newpass%
echo.
set "passtipp=""
set /p "passtipp=New tipp: "
set passtipp=%passtipp:"=%
if exist "tipp.txt" attrib -h -s "tipp.txt"
if not "%passtipp%"=="" (
echo>tipp.txt %passtipp%
) else (
del "tipp.txt"
)
goto SETPASS
:END
这里写的所有内容都已经在 Stack Overflow 上针对带有标签的问题的回答中被写了数千次了批处理文件。在开始批量代码开发之前,最好阅读这里 20 到 30 个答案。
2015年5月8日编辑:
如果此批处理文件的用户输入,这里是一个比上面更好的版本<
or >
在密码中或作为提示。它在必要时使用延迟扩展以避免这 2 个字符被解释为重定向语句。
@echo off
setlocal EnableDelayedExpansion
title Folder Locker by KBKOZLEV
:SETPASS
set "tipp="
set "password="
if exist "password.txt" (
set /p password=<password.txt
attrib +h +s "password.txt"
)
if exist "tipp.txt" (
set /p tipp=<tipp.txt
attrib +h +s "tipp.txt"
)
:START
if exist "Locked" goto OPEN
if exist "Unlocked" goto LOCK
if not exist "Unlocked" goto MDLOCKER
:LOCK
ren "Unlocked" "Locked"
attrib +h +s "Locked"
echo.
echo Folder locked.
CHOICE /C X /T 5 /D X > nul
exit
:MDLOCKER
md "Unlocked"
echo>password.txt 1234
echo>tipp.txt 1234
attrib +h +s "password.txt"
attrib +h +s "tipp.txt"
cls
echo.
echo Private folder created successfully.
CHOICE /C X /T 5 /D X > nul
goto END
:OPEN
cls
echo.
echo Password tipp: %tipp%
echo.
echo Enter password to unlock folder or
echo enter "new" to set a new password.
echo.
set "pass=""
set /p "pass=Password: "
set "pass=!pass:"=!"
if /i "%pass%"=="new" goto NEWPASS
if "%pass%"=="%password%" (
attrib -h -s "Locked"
ren "Locked" "Unlocked"
echo.
echo Folder unlocked successfully.
goto END
)
goto FAIL
:FAIL
cls
echo.
echo Invalid password, please try again.
CHOICE /C X /T 5 /D X > nul
cls
goto OPEN
:NEWPASS
cls
echo.
set "oldpass=""
set /p "oldpass=Old password: "
set "oldpass=!oldpass:"=!"
if not "%oldpass%"=="%password%" goto FAIL
:ENTERNEW
cls
echo.
set "newpass=""
set /p "newpass=New password: "
set "newpass=!newpass:"=!"
if "%newpass%"=="" (
echo.
echo Invalid new password, please enter new password again.
CHOICE /C X /T 5 /D X > nul
goto ENTERNEW
)
if exist "password.txt" attrib -h -s "password.txt"
echo>password.txt !newpass!
echo.
set "passtipp=""
set /p "passtipp=New tipp: "
set "passtipp=!passtipp:"=!"
if exist "tipp.txt" attrib -h -s "tipp.txt"
if not "%passtipp%"=="" (
echo>tipp.txt !passtipp!
) else (
del "tipp.txt"
)
goto SETPASS
:END
endlocal