簡體   English   中英

Bash腳本執行需要幫助

[英]Assistance Required With Bash Script Execution

我有一個腳本,從文件中提取逗號分隔信息並准備更新語句。 該文件設置如下所示:

ID,NAME,DATE,TIME,HOURS,EMPNUMBER
1, Joe, 12/11, 12:45, 5, 333
2, John, 12/12, 16:45, 7, 666

我的腳本將文件作為參數,並從命令行運行,如下所示:

./runScript.sh file.csv

我的腳本代碼如下:

for i in ` cat $1 | grep -v “EMPNUMBER” | cut -d',' -f4,5`
do
   time=`echo $i | cut -d',' -f1`
   hours=`echo $i | cut -d',' -f2`
   echo "update jobs.j j set j.time= $time where j.hours=$hours;"

done

我只是好奇為什么,當我運行我的腳本時,它跳過我文件中的頂行,這是標題信息。 顯然,這是期望的效果,但為了讓我的學習進步,我需要理解為什么從文件中跳過第一行。

有人可以幫助我理解嗎?

如果你正在學習bash,那么除了解釋grep -v "EMPNUM"是導致標題被跳過的原因( -v選項意味着查找不包含 EMPNUM ),還有一些其他項要指出。 首先,良好的bash代碼利用bash提供的工具來讀取輸入和解析數據,而不是依賴於生成子shell來運行其他程序(即cat, grep, cut )。

注意:使用cat, grep, cut沒有任何問題,但是認識到bash本身提供的工具與你正在使用的其他3個程序完全相同,這將增強你的編程技巧。

首先,bash提供了用於從stdin或任何其他文件讀取數據的內置read 要讀取文件,通常會while read var1 var2; do... done <"filename"看到while read var1 var2; do... done <"filename" while read var1 var2; do... done <"filename" for i in $(cat file) while read var1 var2; do... done <"filename"而不是for i in $(cat file) - 出於很多原因。 接下來,bash不是調用cut...而是提供parameter expansion/substring extraction來處理將任何文本行解析為任何單個變量。 此外,通過明智地選擇伴隨read變量,您可以完全消除需要使用substring extraction

下面顯示了在示例中顯示的cat, grep, cut方法的bash替代方法的使用。 如果您有興趣學習bash ,請先看看,如果您有任何疑問,請告訴我。 您可以交替使用echoprintf進行輸出。 雖然echo通常更簡單,但printf提供了許多優點。 值得學習兩個......

#!/bin/bash

## set the datafile name (defaults to 'dat/empdata.dat')
dfn="${1:-dat/empdata.dat}"

## validate that file is readable
[ -r "$dfn" ] || {
    printf "\n error: file not readable '%s'. Usage: %s [filename (dat/empdata.dat)]\n\n" "$dfn" "${0//*\//}"
    exit 1
}

## simple output header for data
printf "\nEmployee data read from file: '%s'\n\n" "$dfn"

## read each line in file, skipping header (where $id = ID)
#  IFS is set to include ',' in addition to default ' \t\n'
while IFS=$' ,\t\n' read -r id nm dt tm hrs eno || [ -n "$hrs" ]; do

    # if header row - skip
    [ "$id" = "ID" ] && continue
    # print out each of the values for the employee
    printf "ID: %s  NAME: %-4s  DATE: %s  TIME: %s  HOURS: %s  EMPNUMBER: %s\n" \
    "$id" "$nm" "$dt" "$tm" "$hrs" "$eno"

done <"$dfn"

輸入文件:

$ cat dat/empdata.dat
ID,NAME,DATE,TIME,HOURS,EMPNUMBER
1, Joe, 12/11, 12:45, 5, 333
2, John, 12/12, 16:45, 7, 666

輸出:

$ bash empdata.sh

Employee data read from file: 'dat/empdata.dat'

ID: 1  NAME: Joe   DATE: 12/11  TIME: 12:45  HOURS: 5  EMPNUMBER: 333
ID: 2  NAME: John  DATE: 12/12  TIME: 16:45  HOURS: 7  EMPNUMBER: 666

使用awk,我試過了

awk -F ',' '{if(NR==1) for(i=1;i<=NF;i++) a[i]=$i}{if(NR>=2)for(i=1;i<=NF;i++) printf("%s:%s\t",a[i],$i)}{printf("\n")}' file.txt

輸出:

ID:1    NAME: Joe   DATE: 12/11 TIME: 12:45 HOURS: 5    EMPNUMBER: 333  
ID:2    NAME: John  DATE: 12/12 TIME: 16:45 HOURS: 7    EMPNUMBER: 666  

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM