优化逐行bash函数的并行化

优化逐行bash函数的并行化,bash,function,gnu-parallel,Bash,Function,Gnu Parallel,我有几十个大小为2-10GB的文件需要重新格式化,而我目前使用的bash脚本对单个文件的处理时间超过1天。将文件重定向到3

我有几十个大小为2-10GB的文件需要重新格式化,而我目前使用的bash脚本对单个文件的处理时间超过1天。将文件重定向到3<似乎开销更大,因此我对这种方法进行了评论。我在这个脚本中还有几个生成${KEYS[@]}的函数,但是我确实需要关于如何优化下面的函数以提高速度的建议

其目的是重新格式化不以指定$INPUT_文件中的注释开头的行。我试图找到最快的方法来并行化这个函数,并期望它一次执行8行函数(8个CPU)

#/bin/bash
函数重新格式化{
#当读取-u 3-r线时;执行以下操作
当读取-r行时;执行
semicolVals=$(echo$行| awk'{print$12}')

IFS=';“read-r-a SCV-d”<许多子进程。你应该能够通过在
awk
中重写来消除大部分/全部。祝你好运。坚持一个进程至少可以得到一个数量级的提升,使用编译语言可能会得到另一个。这是@Sheller和我所指的一个很好的例子:
ColA=$(echo$line | awk'{print$1}')…
As@shelleter编写:用另一种语言重写。如果您选择Perl,更改不会太大。
#!/bin/bash

function reformat {
    #while read -u 3 -r line; do
    while read -r line; do
        semicolVals=$(echo $line | awk '{print $12}')    
        IFS=';' read -r -a SCV -d '' < <(printf '%s' "${semicolVals[@]}")
        VALS=()
        for k in "${KEYS[@]}"; do
            if grep -q "$k=" <<< "${SCV[@]}"; then
                str="${SCV[@]}"
                VAL=${str##*$k=}
                VAL=${VAL%%[[:space:]]*}
                VALS+=("$VAL")
            else
                VAL='0'
                VALS+=("$VAL")
            fi
        done

        outKEY=$(printf ":%s" "${KEYS[@]}")
        outKEY=${outKEY:1}
        outVAL=$(printf ":%s" "${VALS[@]}")
        outVAL=${outVAL:1}
        ColA=$(echo $line | awk '{print $1}')
        ColB=$(echo $line | awk '{print $2}')
        ColC=$(echo $line | awk '{print $3}')
        ColD=$(echo $line | awk '{print $4}')
        ColE=$(echo $line | awk '{print $5}')
        ColF=$(echo $line | awk '{print $6}')
        ColG=$(echo $line | awk '{print $7}')

        if [[ "$RETAIN" -eq 1 ]]; then
            ColH="$semicolVals"
        else
            ColH='0'
        fi

        printf "%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\n" \
        "$ColA" "$ColB" "$ColC" "$ColD" "$ColE" "$ColF" "$ColG" "$ColH" "${outKEY[@]}" "${outVAL[@]}"
    done
}

export -f reformat
#exec 3< <(grep -v -e '^#' "$INPUT_FILE")
#parallel -j 8 ::: reformat
#exec 3<&- 
grep -v -e '^#' "$INPUT_FILE" | parallel -j 8 ::: reformat