在bash中这三种重定向到STDERR的方法有什么区别?

时间:2017-10-25 16:20:48

标签: bash

我一直在bash中使用warn函数。

function warn { [ $# -gt 0 ] && printf '%s\n' "$*" >&2 ; }

但我最近被告知我应该使用以下结构之一。

function warn { [ $# -gt 0 ] && printf >&2 '%s\n' "$*" ; }

function warn { [ $# -gt 0 ] && printf >&2 -- '%s\n' "$*" ; }

我想我理解--(如果传入的参数包含破折号,则不会将其解析为参数)。

但重定向是在printf之后还是在结束之后有什么区别?

2 个答案:

答案 0 :(得分:3)

这两项建议都没有必要。问题--试图解决的问题是你做了类似

的事情
printf "$somestring" >&2

其中$somestring可能被误认为是一个选项(并且出于其他原因不建议这样做)。但是,'%s\n'不是这样的字符串。它作为printf的参数字面传递。

移动>&2什么都不做,因为shell在尝试识别命令的参数之前将其删除。

如果我要建议对你的功能进行任何更改,那么它们就是

  1. 删除近乎无用的function关键字,改为使用POSIX风格的定义。
  2. 坚持使用警告消息的单个参数,而不是假设shell将以您希望的方式连接多个参数。
  3. warn () { [ $# -gt 0 ] && printf '%s\n' "$1" >&2 ; }
    
    warn "Do not do that"  # not warn do not do that
    

答案 1 :(得分:0)

这里没有区别。重定向是由bash解释和使用的特殊语法,应用程序不会在其命令行中观察这些标记。您也可以在命令前加上重定向,即>&2 printf ...