[英]How to read from user within while-loop read line?
I had a bash file which prompted the user for some parameters and used defaults if nothing was given. 我有一个bash文件,它提示用户输入一些参数,如果没有给出任何参数则使用默认值。 The script then went on to perform some other commands with the parameters. 然后该脚本继续使用参数执行一些其他命令。 This worked great - no problems until most recent addition. 这很有效 - 直到最近添加才有问题。
In an attempt to read the NAMES parameter from a txt file, I've added a while-loop to take in the names in the file, but I would still like the remaining parameters prompted for. 为了尝试从txt文件中读取NAMES参数,我添加了一个while循环来接收文件中的名称,但我仍然希望提示其余的参数。
But once I added the while loop, the output shows the printed prompt in get_ans() and never pauses for a read, thus all the defaults are selected. 但是一旦我添加了while循环,输出就会在get_ans()中显示打印的提示,并且永远不会暂停读取,因此会选择所有默认值。
I would like to read the first parameter from a file, then all subsequent files from prompting the user. 我想从文件中读取第一个参数,然后从提示用户读取所有后续文件。
What did I break by adding the while-loop? 通过添加while循环我打破了什么?
cat list.txt |
while read line
do
get_ans "Name" "$line"
read NAME < $tmp_file
get_ans "Name" "$line"
read NAME < $tmp_file
done
function get_ans
{
if [ -f $tmp_file ]; then
rm $tmp_file
PROMPT=$1
DEFAULT=$2
echo -n "$PROMPT [$DEFAULT]: "
read ans
if [ -z "$ans" ]; then
ans="$DEFAULT"
fi
echo "$ans" > $tmp_file
}
(NOTE: Code is not copy&paste so please excuse typos. Actual code has function defined before the main()) (注意:代码不是复制和粘贴,所以请原谅错别字。实际代码在main()之前定义了函数)
You pipe data into your the while
loops STDIN. 您将数据传输到while
循环STDIN。 So the read
in get_ans
is also taking data from that STDIN stream. 因此get_ans
的read
也从该STDIN流中获取数据。
You can pipe data into while on a different file descriptor to avoid the issue and stop bothering with temp files: 您可以在不同的文件描述符上管理数据,以避免问题并停止使用临时文件:
while read -u 9 line; do
NAME=$(get_ans Name "$line")
done 9< list.txt
get_ans() {
local PROMPT=$1 DEFAULT=$2 ans
read -p "$PROMPT [$DEFAULT]: " ans
echo "${ans:-$DEFAULT}"
}
To read directly from the terminal, not from stdin (assuming you're on a *NIX machine, not a Windows machine): 要直接从终端读取,而不是从stdin读取(假设您使用的是* NIX机器,而不是Windows机器):
while read foo</some/file; do
read bar</dev/tty
echo "got <$bar>"
done
When you pipe one command into another on the command line, like: 在命令行上将一个命令传递给另一个命令时,如:
$ foo | bar
The shell is going to set it up so that bar
's standard input comes from foo
's standard output. shell将进行设置,以便bar
的标准输入来自foo
的标准输出。 Anything that foo
sends to stdout will go directly to bar
's stdin. foo
发送到stdout的任何内容都会直接转到bar
的stdin。
In your case, this means that the only thing that your script can read from is the standard output of the cat
command, which will contain the contents of your file. 在您的情况下,这意味着您的脚本可以读取的唯一内容是cat
命令的标准输出,它将包含文件的内容。
Instead of using a pipe on the command line, make the filename be the first parameter of your script. 不要在命令行上使用管道,而是将文件名作为脚本的第一个参数。 Then open and read from the file inside your code and read from the user as normal. 然后打开并从代码中的文件中读取并正常读取用户。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.