在Windows cmd中,如何提示用户输入并在另一个命令中使用结果?


397

我有一个Windows .bat文件,我想接​​受用户输入,然后将该输入的结果用作对其他命令的调用的一部分。

例如,我想接受用户的进程ID,然后针对该ID运行jstack,将jstack调用的结果放入文件中。但是,当我尝试此操作时,它不起作用。

这是我的示例bat文件内容:

@echo off
set /p id=Enter ID: 
echo %id%
jstack > jstack.txt

这就是jstack.txt中显示的内容:

输入ID:是否终止批处理作业(是/否)? 

2
“终止批处理作业(是/否)?” 通常在.bat运行时按ctrl-c时显示。
Jim Buck

2
Jstack.txt将包含jstack 的输出,不包含与批处理文件有关的任何内容,而且您也没有说过Jstack是什么。
sgmoore,2012年

1
这些答案都行不通吗?如果没有,您找到解决方案了吗?如果您这样做了,那么如果您将其作为自我回答发布在这里将会很有帮助。
Maslor 2015年

1
如果您想固定选项,输入你最好不要使用choiceset /p
icc97

2
请标记我的帖子为答案,其本质是在运行批处理程序时,您按Enter而不是在提示符下提供ID,因此%id%被设置为,Enter ID: 而不是您应该从中提供的ID键盘。
pashute

Answers:


458

尝试这个:

@echo off
set /p id="Enter ID: "

然后,您可以将其%id%用作另一个批处理文件的参数,例如jstack %id%

例如:

set /P id=Enter id: 
jstack %id% > jstack.txt

2
有没有一种方法可以将SET命令的输出传递给NIL :,以便隐藏输入?就像您要执行a:set /p id=Enter ID:\r\n set /p pw=Enter Passwd:并且不希望密码文本显示在窗口中一样,更不用说在“ DosKey”命令缓冲区中显示了?除了编写一些C程序以获取输入并将其分配给EnvVar之外,我已经尝试了几种不同的方法,但一直找不到找到这种方法的方法,但这很欺骗!:)我希望它可以与Windows CMD一起使用。
拉里F


4
请注意,末尾增加了一些空格"Enter ID: "。在提示和用户答案之间留出很小的空间。Delete the internet?No sillyDelete the internet? No silly
icc97

无需报价。@Instantsoup缺少的是该行中的'%id%'jstack %id% > jstack.txt
pashute

1
如果希望将变量保留在当前批次的本地,请使用SETLOCALENDLOCAL。见ss64.com/nt/endlocal.html
endo64 '18

99

语法如下: set /p variable=[string]

请访问http://commandwindows.com/batch.htmhttp://www.robvanderwoude.com/userinput.php,以更深入地了解使用不同版本的Windows OS批处理文件的用户输入。

设置变量后,就可以按照以下方式使用它。

@echo off
set /p UserInputPath=What Directory would you like?
cd C:\%UserInputPath%

注意%VariableName%语法


请完成您的句子...您要添加另一个链接吗?另外,我在Windows 7 cmd.exeShell中测试了以上所有内容,并且每个都(无一例外)将用户输入分配给任意命名的变量。您的回应如何修饰已提供的内容?
chb 2012年

3
当我发布答案时,原来的问题似乎并没有真正得到回答。原始问题是“您如何要求用户输入,然后在另一个命令中使用它?” 我相信我的回答简洁地回答了这个问题。另外,当您在Google中搜索“如何从批处理文件中获取用户输入”时,该问题在结果中排​​在第二位,因此它需要正确的答案,尽管该论坛是我想要的。
jayfessenden,2012年

14
后面的空格=不是必需的。
乔伊

我们为什么需要空间?cmd不允许空间的确切原因是什么?
ytpillai 2015年

@Joey我同意,robvanderderwoude.com页面没有空间SET /P variable=[promptString]
icc97

31

我不确定所有版本的Windows是否都是这种情况,但是在我拥有的XP计算机上,我需要使用以下命令:

set /p Var1="Prompt String"

没有引号中的提示字符串,我会根据文本得到各种结果。


+1表示“取决于文本的各种结果”:我也遇到了同样的问题。现在,它用文本打印引号,但是没有其他奇怪的行为了。
2015年

6
使用这个语法引号,但要避免展示他们:set /p "var1=Prompt String"
斯蒂芬·

使用引号并在末尾包含一个空格非常有用,因为这会使命令行上的提示更好。带有引号会使批处理文件中明显有空格。set /p Var1="Prompt String "然后,当您运行文件并且用户键入内容Prompt String Yes而不是Prompt StringYes
icc97

22
set /p choice= "Please Select one of the above options :" 
echo '%choice%'

后面的空间=非常重要。


14
@echo off
set /p input="Write something, it will be used in the command "echo""
echo %input%
pause

如果我得到了您想要的东西,这会很好。您也可以在其他命令中使用%input%。

@echo off
echo Write something, it will be used in the command "echo"
set /p input=""
cls
echo %input%
pause 

8
@echo off
:start
set /p var1="Enter first number: "
pause

2
你为什么开始:start
2015年

1
:start只是一个标记...例如,他可能还使用一个:end,导致诸如变量清除之类的事情发生,或者调用popd或类似的东西。然后,您还可以选择使用 IF ERRORLEVEL1 GOTO END...甚至使用GOTO ERR,并且在:err类似echo的内容下尝试获取文件号时发生错误。goto:end这可能是一种习惯...
LarryF '16

8

与SET一样,SETX没有记录的/ prompt参数。

如果需要提示环境变量在重启后仍然有效,则可以使用SETX进行存储。

在重新启动命令提示符之前,SETX创建的变量将不可用。然而,整洁地,您可以设置一个已经被SET的变量,即使它具有相同的名称。

这在Windows 8.1 Pro中对我有效:

set /p UserInfo= "What is your name?  "
setx UserInfo "%UserInfo%"

(必须将现有变量周围的引号引起来。)

此过程允许您在当前会话期间使用临时的SET创建的变量,并允许您在计算机重新启动或CMD提示符重新启动时重用SETX创建的变量。

(已编辑以正确设置代码段落的格式。)


5

在为客户准备PC时,我使用了一个cmd:它将调用用户进行输入,然后将PC重命名为该cmd。

@ECHO "remember to run this as admin."
@ECHO OFF
SET /P _inputname= Please enter an computername:
@ECHO Du intastede "%_inputname%"
@ECHO "The pc will restart after this"
pause
@ECHO OFF
wmic computersystem where name="%COMPUTERNAME%" call rename name="%_inputname%"

shutdown -r -f

再次嗨,此有用的脚本在初始设置后在Win10 pc上使用:-)
Werdna,

5

有两种可能性。

  1. 您忘记%id%jstack拨打电话。

    jstack %id% > jstack.txt
    

因此,整个正确的批处理文件应为:

@echo off
set /p id=Enter ID: 
echo %id%
jstack %id% > jstack.txt

和/或2.您确实将其放入代码中(并且忘记在问题中告诉我们),但是在运行批处理文件时,您按Enter键而不是输入ID(例如1234)。

这是这两个错误的结果: jstack应该使用您提供的ID进行调用。

但是在您的情况下(根据问题中提供的代码),您没有任何变量地调用了它。你写了:

jstack > jstack.txt

因此,当您jstack不使用任何变量运行时,它将输出以下内容:

Terminate batch file Y/N? 

您的第二个错误是,当程序询问您:时,您按Enter而不是提供一个值 Enter ID:。如果此时要输入一个ID,例如1234,则该%id%变量将成为该值,在我们的例子中为1234。但是您没有提供值,而是按Enter键。如果您不给变量任何值,并且如果该变量之前未设置为其他任何值,则该变量%id%将设置为set命令提示符!因此,现在%id%设置为Enter ID:在调用jstack之前,按批处理文件中的请求在屏幕上回显的对象。

但是我怀疑您的DID jstack %id% > jstack.txt在批处理文件代码中带有%id(并从问题中错误地省略了它),并且您按回车时没有输入id。然后,批处理程序回显该ID(现在为“输入ID:”),然后运行jstack Enter ID: > jstack.txt

Jstack本身回显了输入,遇到一个错误并要求终止。
所有这些都被写入了jstack.txt文件。


3

在我的Vista机器上,变量周围的美元符号不起作用,但百分号起作用。另请注意,在提示和用户输入之间将出现“设置”行上的尾随空格。


尾随空间?win7 x64 rus:C:\>set /p DestPath="Type path:"下一行是Type path:c:\dddd
Arioch'The

2
$符号用于bash或unix变量。%%符号用于Windows变量。
noob 2013年

如果SETLOCAL ENABLEDELAYEDEXPANSION批处理文件中有一个,则可以使用!EnvVariable!它在FOR循环期间将其扩展到其值,或者在Cmd解析器实际处理该行之前,其他不扩展宏的事情。请参阅cmd /?有关此信息以及help setlocal...
LarryF '16

2

刚刚添加了

set /p NetworkLocation= Enter name for network?

echo %NetworkLocation% >> netlist.txt

排序到我的netsh批处理作业。现在,它向我显示了我作为该样本响应点的位置。我不断>>输出文件,因此现在知道“家”,“工作”,“星巴克”等。寻找晴朗的空气,我可以寻找使用最少的信道,以及周围是否有5个或全部2.4 MHz WLAN。


2

只是为了保留变量的默认值。按Enter键以使用最近运行的.bat的默认值:

@echo off
set /p Var1=<Var1.txt
set /p Var1="Enter new value ("%Var1%") "
echo %Var1%> Var1.txt

rem YourApp %Var1%

在第一次运行中,只需忽略有关变量缺少初始值的文件缺失消息(或手动创建Var1.txt)。


(set /p var=<var1.txt) 2>nul将保留错误消息。您也可以给set var1=default而不是从文件中获取东西
Stephan

史蒂芬(Stephan),您建议的第二部分不保留两次运行之间的值!您可以进一步开发吗?
安东尼

不,不在两次跑步之间。它只是给出一个默认值。(没有要求在两次运行之间存储值)。
Stephan'1
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.