1

我有以下平面文件employees.txt

100  Thomas  Manager    Sales       $5,000
200  Jason   Developer  Technology  $5,500
300  Sanjay  Sysadmin   Technology  $7,000
400  Nisha   Manager    Marketing   $9,500
500  Randy   DBA        Technology  $6,000

我想统计每个部门的人数。我知道有更短的方法可以使用类似的命令来执行此操作,awk '{print $4}' employees.txt | sort | uniq -c但我想学习 while 循环的机制,逐行读取输入

#!/bin/bash
awk '{print $4}' employees.txt > temp_file

array=[]
while read line
do
        if [[ $array[$line] ]]
        then
                $array[$line]=$(($array[$line]+1))
        else
                $array[$line]=0
        fi
done < temp_file

当我运行这个脚本时,我得到了错误./process.sh: line 9: [][Sales]+1: syntax error: operand expected (error token is "[][Sales]+1")

另外-在关键字之后是否可以使用语法done来获取第四列中的条目?我试过done < awk '{print $4}' employees.txt了,但这是不正确的。

另外-有没有办法可以将输出存储awk '{print $4}' employees.txt > temp_file在变量而不是临时文件中?

4

4 回答 4

1
#!/bin/bash

awk '{print $4}' employees.txt > temp_file
declare -A array
while read line
do
        if [[ ${array["$line"]} ]]; then
          array["$line"]=$(( ${array["$line"]} + 1 ))
        else
          array["$line"]=1
        fi
done < temp_file

for k in "${!array[@]}"; do
  echo "$k ${array[$k]}"
done
于 2013-03-10T01:30:52.293 回答
1

不需要使用 awk。你可以尝试这样的事情:

#!/bin/bash       # bash 4
declare -A DEPARTMENT
while read -a field
do
  (( DEPARTMENT[${field[3]}]++ ))
done < employees.txt

for dep in "${!DEPARTMENT[@]}"
do
  printf "%s\n" "$dep ${DEPARTMENT[$dep]}"
done
于 2013-03-10T07:56:53.443 回答
0
array=[]

是不正确的。Bash 数组是这样声明的

declare -A array=()

或者也许只是

array=()

另外-在 done 关键字之后是否可以使用语法来获取第四列中的条目?我试过done < awk '{print $4}' employees.txt

您可以尝试进程替换

done < <(awk '{print $4}' employees.txt)
于 2013-03-10T01:16:55.030 回答
0

两个解决方案,第一个 in bash(类似于,但比其他给定解决方案更简洁 - 消除使用awk拉出第四列,而不是使用read)。

一、bash实现:

#!/usr/bin/bash

declare -A dept
while read -r _ _ _ d _; do
   ((dept[$d]++))
done <<-'!'
100  Thomas  Manager    Sales       $5,000
200  Jason   Developer  Technology  $5,500
300  Sanjay  Sysadmin   Technology  $7,000
400  Nisha   Manager    Marketing   $9,500
500  Randy   DBA        Technology  $6,000
!

for d in "${!dept[@]}"; do
   printf '%s %d\n' "$d" "${dept[$d]}"
done

awk实现非常相似:

awk '
   {
      dept[$4]++;
   }
   END {
      for (d in dept)
         print d, dept[d]
   }
' <<'!'
100  Thomas  Manager    Sales       $5,000
200  Jason   Developer  Technology  $5,500
300  Sanjay  Sysadmin   Technology  $7,000
400  Nisha   Manager    Marketing   $9,500
500  Randy   DBA        Technology  $6,000
!
于 2013-03-10T19:33:04.110 回答