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

506

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

例如,我想从用户那里接受一个进程ID,然后运行jstack并将jstack调用的结果放入文件中。 但是,当我尝试时,它不起作用。

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

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

下面是jstack.txt中显示的内容:

输入ID:终止批处理作业(Y/N)?

3
当你运行.bat文件时按下ctrl-c,通常会出现“终止批处理作业(Y/N)?”的提示。 - Jim Buck
2
Jstack.txt 文件将包含 jstack 的输出内容,与您的批处理文件无关,同时您也没有说明 jstack 是什么。 - sgmoore
1
这些答案都没有起作用吗?如果没有,你找到解决方案了吗?如果找到了,如果你能在这里发布一个自我回答,那将会很有帮助。 - Maslor
1
如果您想要输入固定选项,最好使用 choice 而不是 set /p - icc97
2
请将我的帖子标记为答案,其要点是在运行批处理程序时,您按Enter键而不是在提示符处提供ID,因此%id%被设置为“输入ID:”而不是您应该从键盘上提供的某个ID。 - pashute
1
@pashute 的账户似乎已经被删除了,哈哈 - zvava
14个回答

601

尝试这样做:

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

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

例如:

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

4
有没有办法将"SET"命令的输出导向到NIL:,这样就可以隐藏输入的内容?比如,如果你想执行以下命令: set /p id=Enter ID:\r\n set /p pw=Enter Passwd: 但是不想在窗口中显示密码文本,更不要让其显示在"DosKey"命令缓冲区中。我尝试过几种不同的方法,但是除了编写一个小的C程序来获取输入并将其赋值给EnvVar之外,我没有找到其他方法,但那样做有点作弊!:) 我希望只使用Windows CMD就能实现。 - LarryF
@LarryF 请查看以下链接:https://dev59.com/JWIj5IYBdhLWcg3wuXaN 和 https://dev59.com/NXRB5IYBdhLWcg3wUFrB - Instantsoup
5
注意"Enter ID: "末尾添加的空格,可以在提示和用户回答之间增加一个可爱的小空格。Delete the internet?No sillyDelete the internet? No silly的区别是前者缺少空格。请注意保持原意,但使语言更通俗易懂。 - icc97
2
如果您想将变量限定在当前批处理中,请使用SETLOCALENDLOCAL。请参阅https://ss64.com/nt/endlocal.html。 - endo64
像往常一样,记得使用双引号,如果用户输入包含空格:echo hello > "%fname%" - gog
显示剩余2条评论

123
语法如下:set /p variable=[string] 查看以下网站以深入了解在不同版本的Windows操作系统批处理文件中使用用户输入:http://commandwindows.com/batch.htm 或者 http://www.robvanderwoude.com/userinput.php 一旦设置了变量,你可以按照以下方式使用它。
@echo off
set /p UserInputPath=What Directory would you like?
cd C:\%UserInputPath%

请注意%VariableName%的语法


请完成你的句子...你打算包含另一个链接吗?此外,我在 Windows 7 的 cmd.exe shell 中测试了以上所有内容,并且每个命令都将用户输入分配给一个任意命名的变量,没有例外。你的回答如何添油加醋地补充了已经提供的内容? - chb
3
当我发布了我的回答时,似乎原始问题并没有得到解答。原始问题是“如何请求用户输入,然后再把它用于另一个命令中?”我相信我的回答简洁地回答了这个问题。此外,当你在谷歌上搜索“如何从批处理文件中获取用户输入”时,这个问题排名第二,因此它需要正确的答案,我认为这个论坛就是为此而设立的。 - jayfessenden
14
=后面的空格不是必需的。 - Joey
为什么我们需要空格?在 cmd 中究竟发生了什么不允许使用空格的事情? - rassa45
@Joey 我同意,robvanderderwoude.com页面中没有空格 SET /P variable=[promptString] - icc97

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

等号后面的空格非常重要。


35

我不确定这是否适用于所有版本的Windows,但在我的XP机器上,我需要使用以下内容:

set /p Var1="Prompt String"

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


+1 表示“根据文本不同会有各种结果”:我曾经遇到过同样的问题。现在它会打印带有文本的引号,但不再出现奇怪的行为了。 - Benj
8
使用以下语法来“拥有”引号,但避免“显示”它们:set /p "var1=提示字符串" - Stephan
在命令行中使用引号并在末尾包含一个空格是很有用的,因为它使提示更加友好。在批处理文件中使用引号可以明确地表示该处有一个空格。例如:set /p Var1="Prompt String " 当运行文件并且用户输入内容时,你会得到 Prompt String Yes 而不是 Prompt StringYes - icc97

15
@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 

10
你也可以尝试使用userInput.bat,它使用html输入元素。

这里输入图片描述

这将把输入值分配给jstackId变量。
call userInput.bat jstackId
echo %jstackId%

这将只打印输入值,您最终可以通过FOR /F捕获:

call userInput.bat

2
优秀的解决方案。谢谢! - Jean-François

9

对于SETX命令而言,与SET有记录/提示参数不同的是,并没有相关文档。

如果您需要提示输入环境变量并且需要该变量可在重启后生效,可以使用SETX来存储该变量。

通过SETX创建的变量在重新启动命令提示符之前无法使用。但是请注意,即使变量名称相同,也可以将已经SET的变量用SETX重新设置。

在Windows 8.1 Pro中,这个方法适用。

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

(现有变量周围的引号是必需的。)

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

(已编辑以正确格式化代码段落。)


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

3
为什么你要以 :start 开始? - Benj
1
:start 只是一个标记... 例如,他可能也会使用 :end,这会导致变量清理等事情发生,或者调用 popd 等类似的操作。然后,您还可以选择使用 IF ERRORLEVEL1 GOTO END... 或者 GOTO ERR,在 :err 下面添加类似以下内容: echo 尝试获取文件号时发生错误。 goto:end 这可能只是一种习惯... - LarryF

6
有两种可能性。
  1. You forgot to put the %id% in the jstack call.

    jstack %id% > jstack.txt
    

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

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

并且/或者2. 你已经将它放入了代码中(但在问题中忘记告诉我们),但是当你运行批处理文件时,你按下了回车键而不是输入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之前在批处理文件中请求在屏幕上显示。
但我怀疑你在批处理文件中确实使用了jstack %id% > jstack.txt(并且在问题中不小心省略了它),然后在没有输入ID的情况下按下了Enter键。批处理程序随后回显了ID,即“Enter ID:”,然后运行了jstack Enter ID: > jstack.txt
Jstack本身回显了输入,遇到了错误并要求终止。而所有这些都被写入了jstack.txt文件中。

5

在我为客户准备电脑时,我有一个小的命令行程序:它调用用户输入并将计算机重命名为该名称。

@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 电脑上经过初始设置后使用 :-) - Werdna

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接