lik*_*ern 38 bash shell pipe bash-function
我有一些bash函数输出一些信息:
我一直在编写读取输出和过滤它的函数:
function filter-epson {
find-modelname-in-epson-ppds | sed <bla-blah-blah>
}
function filter-hp {
find-modelname-in-hp-ppds | sed <the same bla-blah-blah>
}
etc ...
Run Code Online (Sandbox Code Playgroud)
但我认为最好做这样的事情:
function filter-general {
(somehow get input) | sed <bla-blah-blah>
}
Run Code Online (Sandbox Code Playgroud)
然后调用另一个高级函数:
function high-level-func {
# outputs filtered information
find-modelname-in-hp/epson/...-ppds | filter-general
}
Run Code Online (Sandbox Code Playgroud)
如何通过最好的bash实践实现这一目标?
dav*_*all 47
如果问题是How do I pass stdin to a bash function?,那么答案是:
Shellscript函数以普通方式使用stdin,就好像它们是命令或程序一样.:)
input.txt中:
HELLO WORLD
HELLO BOB
NO MATCH
Run Code Online (Sandbox Code Playgroud)
test.sh:
#!/bin/sh
myfunction() {
grep HELLO
}
cat input.txt | myfunction
Run Code Online (Sandbox Code Playgroud)
输出:
hobbes@metalbaby:~/scratch$ ./test.sh
HELLO WORLD
HELLO BOB
Run Code Online (Sandbox Code Playgroud)
请注意,命令行参数也以普通方式处理,如下所示:
test2.sh:
#!/bin/sh
myfunction() {
grep "$1"
}
cat input.txt | myfunction BOB
Run Code Online (Sandbox Code Playgroud)
输出:
hobbes@metalbaby:~/scratch/$ ./test2.sh
HELLO BOB
Run Code Online (Sandbox Code Playgroud)
Buv*_*inJ 16
将stdin 放入变量的一个非常简单的方法是使用read. 默认情况下,它读取文件描述符“0”,即标准输入即/dev/stdin.
示例函数:
input(){ local in; read in; echo you said $in; }
Run Code Online (Sandbox Code Playgroud)
示例实现:
echo "Hello World" | input
Run Code Online (Sandbox Code Playgroud)
结果:
你说你好世界
当然,您不需要将变量声明为本地变量。我只是为了良好的形式而将其包括在内。简单的老read in做你需要的。
所以你理解read它是如何工作的,默认情况下它从给定的文件描述符(或隐式标准输入)读取数据并阻塞,直到遇到换行符。很多时候,您会发现它会隐含地附加到您的输入中,即使您不知道它。如果您有一个似乎与此机制有关的功能,请记住这个细节(还有其他方法read可以解决这个问题......)。
除了基本示例之外,还有一个变体,可让您通过 stdin 或参数传递输入:
input()
{
local in=$1 if [ -z "$in" ]; then read in; fi
echo you said $in
}
Run Code Online (Sandbox Code Playgroud)
通过该调整,您还可以调用该函数,例如:
input "Hello World"
Run Code Online (Sandbox Code Playgroud)
如何处理 stdin 选项和其他参数?许多标准的 nix 实用程序,尤其是那些通常与 stdin/stdout 一起使用的实用程序,都遵循将破折号处理为-“默认”的常见做法,这在上下文中意味着 stdin 或 stdout,因此您可以遵循约定,并将指定的参数视为-意思是“标准输入”:
input()
{
local a=$1; if [ "$a" == "-" ]; then read a; fi
local b=$2
echo you said $a $b
}
Run Code Online (Sandbox Code Playgroud)
像这样调用:
input "Hello" "World"
Run Code Online (Sandbox Code Playgroud)
或者
echo "Hello" | input - "World"
Run Code Online (Sandbox Code Playgroud)
更进一步,实际上没有理由仅将 stdin 限制为仅作为第一个参数的选项!您可能会创建一个超级灵活的功能,可以将其用于其中任何一个...
input()
{
local a=$1; if [ "$a" == "-" ]; then read a; fi
local b=$2; if [ "$b" == "-" ]; then read b; fi
echo you said $a $b
}
Run Code Online (Sandbox Code Playgroud)
你为什么要那样?因为您可以制定并输入您可能需要的任何论点......
myFunc | input "Hello" -
Run Code Online (Sandbox Code Playgroud)
在这种情况下,我在第二个参数中使用的结果进行管道传输,myFunc而不是唯一具有第一个选项的选项。
gle*_*man 15
要痛苦地说明我是从斯坦丁那里来的,我有时会写
cat - | ...
Run Code Online (Sandbox Code Playgroud)
sed直接打电话.而已.
function filter-general {
sed <bla-blah-blah>
}
Run Code Online (Sandbox Code Playgroud)