在awk中返回两个变量

时间:2012-01-25 11:07:08

标签: bash shell awk

目前这就是我正在做的事情

ret=$(ls -la | awk '{print $3 " "  $9}')
usr=$(echo $ret | awk '{print $1}')
fil=$(echo $ret | awk '{print $2}')

问题是我没有运行ls运行需要时间的命令,所以你可以理解逻辑。

有没有办法可以设置返回值来设置两个外部值,例如

ls -la | awk -r usr=x -r fil=y '{x=$3; y=$9}'

这样命令将运行一次,我可以将它最小化为一行

6 个答案:

答案 0 :(得分:5)

它并不漂亮,但如果您真的需要在一行中执行此操作,则可以使用awk / bash的高级元编程功能:)

eval $(ls -la | awk '{usr = $3 " " usr;fil = $9 " " fil} END{print "usr=\""usr"\";fil=\""fil"\""}')

要打印:

echo -e $usr
echo -e $fil

就个人而言,我坚持使用你所拥有的东西 - 与上述相比,它更具可读性和性能开销很小:

$time <three line approach>

real    0m0.017s
user    0m0.006s
sys     0m0.011s

$time <one line approach>
real    0m0.009s
user    0m0.004s
sys     0m0.007s

答案 1 :(得分:2)

使用read

的变通方法
usr=""
fil=""
while read u f; do usr="$usr\n$u"; fil="$fil\n$f"; done < <(ls -la | awk '{print $3 " "  $9}')

对于性能问题,您可以使用<<<,但如果返回的文本很大,请避免使用它:

while read u f; do usr="$usr\n$u"; fil="$fil\n$f"; done <<< $(ls -la | awk '{print $3 " "  $9}')

来自@ WilliamPursell答案的更便携的方式:

$ usr=""
$ fil=""
$ while read u f; do usr="$usr\n$u"; fil="$fil\n$f"; done << EOF
> $(ls -la | awk '{print $3 " "  $9}')
> EOF

答案 2 :(得分:2)

使用bash v4 关联数组

unset      FILES
declare -A FILES
FILES=( ls -la | awk '{print $9 " "  $3}' )

打印所有者列表&amp;文件:

for fil in ${!FILES[@]}
do
  usr=${FILES["$fil"]}
  echo -e "$usr" "\t" "$fil"
done

道歉,我无法在计算机上测试,因为bash v3.2不支持关联数组 :-(。 请报告任何问题......

答案 3 :(得分:2)

接受的答案使用进程替换,这是一种仅适用于某些平台的基础。更便携的解决方案是使用heredoc:

read u f << EOF
$( ls ... )
EOF

尝试尝试:

ls ... | read u f

但是读取然后在子shell中运行。一种常见的技术是:

ls ... | { read u f; # use $u and $f here; }

但为了使变量在脚本的其余部分可用,插值的heredoc是最便携的方法。请注意,它需要shell将程序的所有输出读入内存,因此如果预期输出很大或者进程长时间运行,则不适合。

答案 4 :(得分:2)

您要做的是捕获ls或任何其他命令的输出,然后再处理它。

  def determineKind2( a:Int ):Any = {
    val aResult = { if( a < 5 ) 
      a.toInt  // Execution flows here
    else if(a<50)
      a.toLong
    else if(a<100)
      a.toFloat
    else
      println("Oops!") // Never executed--yet I get a Double back!
      a.toDouble  
    }
    aResult
  }

答案 5 :(得分:1)

您可以使用bash数组或位置参数作为临时保留位置:

ret_ary=( $(command | awk '{print $3, $9}') )
usr=${ret_ary[0]}
fil=${ret_ary[1]}

set -- $(command  | awk '{print $3, $9}')
usr=$1
fil=$2