1

我正在尝试将一组连接的变量存储到一个新的 SET 变量中。当我将一个变量添加到另一个变量中时,它似乎实际上并没有正确设置。我很好奇 BATCH 是否可以在变量中存储变量,或者我是否必须进行超出我目前所拥有的格式化:

示例:“oldDirectory”变量应显示与 "%progdata%\%datetime%"

@echo off

For /f "tokens=2-4 delims=/ " %%a in ("%DATE%") do (
    SET YYYY=%%c
    SET MM=%%a
    SET DD=%%b
)
For /f "tokens=1-3 delims=/:." %%a in ("%TIME%") do (
    SET HH24=%%a
    SET MI=%%b
    SET SS=%%c
)

SET datetime=%YYYY%%MM%%DD%_%HH24%%MI%%SS%
SET progdata=C:\ProgramData

@echo on    

IF EXIST  "%progdata%" ( 
echo Found  %progdata%
SET oldDirectory="%progdata%\%datetime%"
echo %oldDirectory%
) 
pause
4

3 回答 3

2

尝试:

CALL SET oldDirectory="%progdata%\%datetime%"
CALL ECHO %oldDirectory%
于 2013-08-14T17:08:34.420 回答
2

第一种方法:

IF EXIST  "%progdata%" ( 
echo Found  %progdata%
SET oldDirectory="%%progdata%%\%%datetime%%"
call echo %oldDirectory%
) 

第二种方法:

IF EXIST  "%progdata%" ( 
echo Found  %progdata%
SET oldDirectory="!progdata!\!datetime!"
setlocal EnableDelayedExpansion
echo %oldDirectory%
) 

有趣的一点是,该echo %oldDirectory%命令显示的当前值progdatadatetime具有相同值的变量oldDirectory

编辑添加示例

@echo off

set progdata=C:\ProgramData

echo First method:
SET oldDirectory="%%progdata%%\%%date:/=%%_%%time::=%%"
call echo %oldDirectory%

echo Second method:
SET oldDirectory="!progdata!\!date:/=!_!time::=!"
setlocal EnableDelayedExpansion
echo %oldDirectory%

输出:

First method:
"C:\ProgramData\14082013_211303.20"
Second method:
"C:\ProgramData\14082013_211303.21"
于 2013-08-14T17:26:46.133 回答
1

您有一个标准DELAYED EXPANSION问题,在 SO 上无休止地讨论。

当批处理遇到"Block statement"- 这通常是一个带括号的语句,分布在许多行上,例如你的,IF EXIST那么整个语句被解析到右括号,此时,ANY%var%替换为该变量的值已解析

因此,您ECHO %olddirectory%被替换为ECHO因为在解析时olddirectory没有值,另一方面执行ECHO将报告是在解析时设置的,因此被替换为ECHO is On/Off progdataecho Found %progdata%echo Found C:\ProgramData

最简单的解决方法是将ECHO语句移到block

IF EXIST  "%progdata%" ( 
 echo Found  %progdata%
 SET oldDirectory="%progdata%\%datetime%"
)
echo Olddirectory=%oldDirectory%

(我添加了,olddirectory=以便echo语句找到要回显的内容(如果olddirectory未设置))

显示值的第二种最简单的方法是

IF EXIST  "%progdata%" ( 
 echo Found  %progdata%
 SET oldDirectory="%progdata%\%datetime%"
 CALL echo %%oldDirectory%%
)

这里,ECHO命令不是在 的上下文中展开IF,而是在从上下文的CALL运行时值获取其环境的IF上下文中。

显示值的第三种最简单的方法是使用命令delayedexpansion选项。setlocalNT 批处理命令通常启动

@echo off
setlocal

它抑制echoing并建立了一个局部环境。当在's 上下文endlocal中到达文件或文件结尾时,将撤销对本地环境的任何更改。setlocal如果一直遵循这个口头禅,我们就不会遇到这样的情况:一个变量由一个批次建立,而下一个批次的环境是“肮脏的”。考虑在同一cmd会话中运行您的原始文件两次。progdata,并且您正在建立的所有其他变量将在第二次到来时保持设置 - 因此olddirectory可能由您的第一次调用设置,并保留该陈旧数据,如果由于某种原因它没有在第二次显式设置。setlocal为您支持所有这些更改。

setlocal enabledelayedexpansion为混合增加了额外的设施。而%var%解析为 的PARSE-TIMEvar,如果delayedexpansion已被调用,则!var!解析为RUN-TIME值 - 因为它在FOR循环中更改...

因此,添加

SETLOCAL ENABLEDELAYEDEXPANSION

在一个战略点(@echo off直到你离开你的训练轮之后......)将允许你对显示进行简单的更改olddirectory

IF EXIST  "%progdata%" ( 
 echo Found  %progdata%
 SET oldDirectory="%progdata%\%datetime%"
 echo !oldDirectory!
) 
于 2013-08-15T14:05:52.990 回答