linux - 试图将 700,000 个数据与 1500 万个数据删除

标签 linux shell

我正在尝试删除从单个文件中获得的 700,000 条数据,这些数据需要针对多个文件中存在的 1500 万条数据进行删除。

示例:700 000 的 1 个文件称为 A。具有 1500 万的多个文件池称为 B。 我想要一个没有文件 A 数据的文件池 B。

下面是我尝试使用的 shell 脚本,它工作正常。但这需要花费 8 多个小时的大量时间进行擦洗。

IFS=$'\r\n' suppressionArray=($(cat abhinav.csv1))
suppressionCount=${#suppressionArray[@]}
cd /home/abhinav/01-01-2015/
for (( j=0; j<$suppressionCount; j++));
do
   arrayOffileNameInWhichSuppressionFound=`grep "${suppressionArray[$j]},"  *.csv| awk -F ':' '{print $1}' > /home/abhinav/fileNameContainer.txt`
    IFS=$'\r\n' arrayOffileNameInWhichSuppressionFound=($(cat /home/abhinav/fileNameContainer.txt))
    arrayOffileNameInWhichSuppressionFoundCount=${#arrayOffileNameInWhichSuppressionFound[@]}
    if [ $arrayOffileNameInWhichSuppressionFoundCount -gt 0 ];
    then
        echo -e "${suppressionArray[$j]}" >> /home/abhinav/emailid_Deleted.txt
        for (( k=0; k<$arrayOffileNameInWhichSuppressionFoundCount; k++));
        do
            sed  "/^${suppressionArray[$j]}/d" /home/abhinav/06-07-2015/${arrayOffileNameInWhichSuppressionFound[$k]} > /home/abhinav/06-07-2015/${arrayOffileNameInWhichSuppressionFound[$i]}".tmp" && mv -f /home/abhinav/06-07-2015/${arrayOffileNameInWhichSuppressionFound[$i]}".tmp" /home/abhinav/06-07-2015/${arrayOffileNameInWhichSuppressionFound[$i]}

       done
     fi
done

我想到的另一个解决方案是将 700k 数据分解为 50K 的较小文件,并发送到 5 个可用的服务器上,同时 POOL A 将在每个服务器上可用。 每个服务器将提供 2 个较小的文件。

最佳答案

这两行很奇特:

arrayOffileNameInWhichSuppressionFound=`grep "${suppressionArray[$j]},"  *.csv| awk -F ':' '{print $1}' > /home/abhinav/fileNameContainer.txt`
IFS=$'\r\n' arrayOffileNameInWhichSuppressionFound=($(cat /home/abhinav/fileNameContainer.txt))

第一个为一英里长的变量名分配一个空字符串,因为标准输出被定向到文件。第二个然后将该文件读入数组。 ('很好奇名字不是arrayOfFileNameInWhichSuppressionFound,但是file的小写f是一致的,所以我猜不是除了使变量名称更难阅读之外,这很重要。)

可以简化为:

ArrFileNames=( $(grep -l "${suppressionArray[$j]}," *.csv) )

您不需要在 IFS 中继续使用回车符;要么永久设置它,要么确保在开始之前没有回车。


您正在运行这些循环 7,00,000 次(使用印度表示法)。好多啊。难怪要花几个小时。您需要将事物组合在一起。

您可能应该简单地从 abhinav.csv1 中提取行并安排将它们转换为适当的 sed 命令,然后将它们拆分并应用它们。沿着:

sed 's%.*%/&,/d%' abhinav.csv1 > names.tmp
split -l 500 names.tmp sed-script.

for script in sed-script.*
do
    sed -f "$script" -i.bak *.csv
done

这使用 -i 选项来备份文件。如果您的 sed 不支持 -i 选项,则可能需要显式进行重定向:

    for file in *.csv
    do
        sed -f "$script" "$file" > "$file.tmp" &&
        mv "$file.tmp" "$file"
    done

您应该试验一下脚本的大小。我在 split 命令中选择了 500 作为适度的折衷。除非您使用的是老式 HP-UX,否则应该是安全的,但您可以增加脚本的大小,这将减少您必须编辑每个文件的次数,从而加快处理速度。如果你可以使用 5,000 或 50,000,你应该这样做。实验看上限是多少。我不确定您是否会发现一次处理所有 700,000 行是否可行 — 但如果您能那样做,那应该是最快的。

关于linux - 试图将 700,000 个数据与 1500 万个数据删除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31309159/

相关文章:

regex - 如何使用 sed/regex 查找最后的多行匹配项?

Python 记录到同一个文件,不同的用户

linux - 当在 stdin 上传输数据时,调用 ausearch 的脚本的行为有所不同

c - shell 如何处理重定向

linux - 如何将终端中定义的变量读取到 bash 脚本

c - 从 C 程序中写入 ip 地址的最简单方法是什么?

进行文件操作时,C++ 程序在 Windows 和 Linux 上运行速度慢得多?

linux - 如何打印仅包含字母的单词?

Linux:使用 cut 命令删除某些字符之前和之后的所有内容

bash - 仅当“git diff”输出某些内容时,如何运行另一个 git 命令?