首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >通过输入控制台的选项从stdin中选择选定的项

通过输入控制台的选项从stdin中选择选定的项
EN

Unix & Linux用户
提问于 2020-06-05 22:47:52
回答 1查看 252关注 0票数 1

有人能指给我一个“挑选”过滤脚本,它能像下面所描述的那样工作吗?

我花了大约一个小时来寻找一个简单的bash脚本/过滤器,这个脚本/过滤器允许我输入一个值列表,并根据我在控制台上所做的选择,将其中的一个子集吐出来。我知道有用C编写的例子,但我想要一个大多数可移植的bash脚本,我可以在Cygwin / Gitbash等等中使用(上下文:我希望能够在某些子目录中运行一些命令,并且我希望将运行命令的目录的选择与要运行的命令的选择分开)。

作为假设用法的例子:

代码语言:javascript
复制
$ echo "foo
> bar
> baz" | pick.sh
* Options:
* 1. foo
* 2. bar
* 3. baz
* Choices? 2 3 
bar
baz

标记为*的行应该是脚本交互地让我选择要“选择”的元素的位置,一旦确定了第2行和第3行,它就会继续将这些元素发送到STDOUT。

理想情况下,可以将空格分隔的数字(如2,3,4 )和包含范围(如2-4 )结合起来。或者甚至可以使用某种类型的自动完成,允许输入项目的前几个字母。

嗯,它在那里,我认为它将是一个非常有用的bash管道过滤器在一般!

(谢谢你读了这么多.)

EN

回答 1

Unix & Linux用户

回答已采纳

发布于 2020-06-06 00:02:41

使用sed行说明符的自演示示例(其中N,M表示行N到M):

代码语言:javascript
复制
$ ./pick.sh < ./pick.sh
Lines:
     1  #!/usr/bin/env bash
     2  
     3  set -o errexit -o nounset -o noclobber
     4  
     5  trap 'rm --force --recursive "$working_directory"' EXIT
     6  working_directory="$(mktemp --directory)"
     7  input_file="${working_directory}/input.txt"
     8  
     9  cat > "$input_file"
    10  
    11  echo 'Lines:'
    12  cat --number "$input_file"
    13  
    14  IFS=' ' read -p 'Choices: ' input < /dev/tty
    15  lines=($input)
    16  
    17  sed --quiet "$(printf '%sp;' "${lines[@]}")" "$input_file"
Choices: 1 5,7 17
#!/usr/bin/env bash
trap 'rm --force --recursive "$working_directory"' EXIT
working_directory="$(mktemp --directory)"
input_file="${working_directory}/input.txt"
sed --quiet "$(printf '%sp;' "${lines[@]}")" "$input_file"

基本上,将标准输入保存到临时文件,打印带有行号的文件,提示输入范围,并将输入范围传递给sed以打印每个输入范围。

这种方法的一个特点是,行将按照它们在文件中出现的顺序打印,而不是按您指定的顺序打印:

代码语言:javascript
复制
…
Choices: 3 1
#!/usr/bin/env bash
set -o errexit -o nounset -o noclobber

如果您确实需要输入顺序,那么在lines上循环是很简单的,尽管这当然不那么有效。

脚本假定您安装了GNU catsed等。如果您使用的是BSD工具,则命令标志将有所不同。

票数 1
EN
页面原文内容由Unix & Linux提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://unix.stackexchange.com/questions/591160

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档