shell脚本性能改进



我开发了下面的脚本来预处理文件我试图从文件的标题中提取时间戳,并根据时间戳的长度删除每行末尾的一些字符。删除后,它会将时间戳附加到文件中的每一行。这个脚本需要将近30分钟来处理一个4GB的文件。有什么方法可以提高性能吗?这个剧本写得更好吗?

if [ -f INPUT.TXT ]; then
echo "FILE exists."
date=$(cut -c8-25 INPUT.TXT | head -1)
date_format=$(echo $date | sed -e "s/./:/g")
echo -e " header date value is : $date"
echo -e "Header date value format is: $date_format"
leng_t=${#date_format}
len=`expr $leng_t + 1`
sed -i "s/.{${len}}$//" INPUT.TXT
sed -i s/$/$date_format/ INPUT.TXT
else
echo "FILE does not exist."
fi
  • 主优化是通过将两个连续的sed组合为一个来获得的
    相反:
    sed -i "s/.{${len}}$//" INPUT.TXT
    sed -i s/$/$date_format/ INPUT.TXT
    
    使用:
    sed -i "s/.{$len}$/$date_format/" INPUT.TXT
    
    这样可以将执行时间缩短两倍
    此结果是显示所有后续优化增益的基本结果

所有后续优化都需要额外的磁盘空间来存储INPUT.TXT文件的副本(即额外的4GB(:

  • 尝试将结果放在一个单独的文件中,而不是将其编辑到位:
    sed "s/.{$len}$/$date_format/" INPUT.TXT >INPUT.tmp.TXT
    mv -f INPUT.tmp.TXT INPUT.TXT
    
    这样可以节省约10%的相对基本结果
  • 在多核机器上,这应该运行得更快:
    rev INPUT.TXT | sed "s/^.{$len}//" | rev | sed "s/$/$date_format/" >INPUT.tmp.TXT
    mv -f INPUT.tmp.TXT INPUT.TXT
    
    这样可以节省约35%的相对基本结果
  • 在多核机器上,如果替换中没有多字节字符(因为cut仍然无法处理(:
    let cut_len=$len+1
    rev INPUT.TXT | cut -c $cut_len- | rev | sed "s/$/$date_format/" >INPUT.tmp.TXT
    mv -f INPUT.tmp.TXT INPUT.TXT
    
    这样可以节省约50%的相对基本结果

因此,通过最佳优化,脚本的运行速度可以提高四倍
注意:所有测试都使用400MB文件完成。

相关内容

  • 没有找到相关文章

最新更新