免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 3649 | 回复: 14
打印 上一主题 下一主题

更新百万行的文件 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2010-01-26 10:34 |只看该作者 |倒序浏览
win环境

1. old.log

内容
一部分如下
"\d{12}"        "\d{8}"        "\w{32}"         "balabala"..."balabala"
还有一部分 跟上面的差异就是第三列是空

两种格式的内容 混合排列 无规律
共1M行

现在有
2. update.log
两列
"\d{12}"        "\w{32}"
是对old.log中那些第三列为空的数据的对应补充  当然old.log.d{12}=update.log.d{12}

现在想把update.log中的内容插入到old中的对应行对应列中
而old.log中第三列不为空 的数据不变

实现不难 难的是效率太低了 几分钟才更新了几十行
我是用数组循环+Tie::File实现的

请教有没有 效率好点的办法
多谢

论坛徽章:
0
2 [报告]
发表于 2010-01-26 10:38 |只看该作者
估计你是更新完一行就写一行吧

论坛徽章:
0
3 [报告]
发表于 2010-01-26 10:57 |只看该作者

回复 #1 perlw01f 的帖子

:wink:
笨办法  把两张表导入到数据库,更新后再导出。

论坛徽章:
0
4 [报告]
发表于 2010-01-26 11:09 |只看该作者
在 Tie::File中 用s///的办法 效率太低了
两张表导入到数据库。。。这样的文件还有不少呢。。。 导入也慢啊

论坛徽章:
0
5 [报告]
发表于 2010-01-26 11:16 |只看该作者

回复 #4 perlw01f 的帖子

呵呵  
对于固定格式的文件  我比较喜欢这样做   比较省心 O(∩_∩)O
我用的是oracle,用load比import快多了。

或者你可以把你的代码贴出来大家看看,不然不知道你的资源消耗在那里

论坛徽章:
0
6 [报告]
发表于 2010-01-26 11:28 |只看该作者

回复 #1 perlw01f 的帖子

要不你试下用OPEN吧
遍历文件1,如果1的第3列为空就检查文件2是否有对应的数据,有就整合后保存进一个数组,如果第3列不为空就直接存入数组。
数组满一定数量(看你的机器性能了)就写入文件,清空数组。

:wink:

论坛徽章:
0
7 [报告]
发表于 2010-01-26 19:35 |只看该作者
#!/usr/bin/perl
#update.log
#old.log
use strict;
use warnings;
use Tie::File;
$|++;

my (@f1, @f2);
tie @f1, 'Tie::File', "old.log" or die "Die!\n";
tie @f2, 'Tie::File', "update.log" or die "Die!\n";

for my $j (0..$#f2) {
    chomp($f2[$j]);
    my ($id1, $id3)= ($f2[$j]=~ m/^(\d+)\t(\w{32})/); #分隔update.log中的两列数据

    for my $i (0..$#f1) {
        chomp($f1[$i]);
        if ($f1[$i]=~ m/'$id1.*?\'(\d+)\'\t''/) {     #匹配old.log中第三列为空
          my $match= $&;
          my $id2= $1;
          $f1[$i]=~ s/$match/\'$id1\'\t\'$id2\'\t\'$id3\'/; #替换对应的第三列
          last;
        }
    }
    $f2[$j]= undef; #去掉update.log中更新了的数据
}

untie @f1;
untie @f2;


初学后进
多谢

[ 本帖最后由 perlw01f 于 2010-1-26 19:40 编辑 ]

论坛徽章:
0
8 [报告]
发表于 2010-01-26 20:17 |只看该作者
你用了两个 for, 当然会慢了,你不如听三楼的意见了

论坛徽章:
0
9 [报告]
发表于 2010-01-26 20:35 |只看该作者
多谢楼上 可否不借助MySQL之类的。。。那个倒是简单,把col1作为 primary key
update table1 set table1.col3=table2.col2 where table1.col1=table2.col1 and table1.col3='';
可是import估计有困难,数据库太大了 这样的old.log估计有好几个G 不知道效率是不是也会很低。。。

论坛徽章:
0
10 [报告]
发表于 2010-01-27 10:31 |只看该作者

回复 #9 perlw01f 的帖子

本帖最后由 toniz 于 2010-02-02 12:38 编辑

you may try this::wink:

  1. #!/usr/bin/perl
  2. use strict;

  3. open FILE1,"old.log" or die "can't open file: old.log .$!";
  4. open FILE2,"update.log" or die "can't open file: update.log .$!";
  5. open FILE3,">>result.log" or die "can't open file: update.log .$!";
  6. my  @result;
  7. my $count = 0;
  8. while (my $tmp = <FILE1>) {
  9.   my ($col1,$col2,$col3) = ($tmp =~/^(\d+)\t(\d+)\t(.*?)\t/);
  10.   if(!$col3){
  11.     seek (FILE2,0,0);
  12.     my @rp = grep /^$col1/,<FILE2>;
  13.     my $rp = pop @rp;
  14.     my $rp_c3= $1 if($rp =~ /^\d+\t(\w{32})/);
  15.     $tmp =~ s/(^\d+\t\d+\t).*?(\t.*)/$1$rp_c3$2/;
  16.   }
  17.   push @result,$tmp;
  18.   $count++;
  19.   if($#result >2){
  20.     print FILE3 @result;
  21.     $count = 0;
  22.     @result=();
  23.   }
  24. }
  25. print FILE3 @result;
  26. close FILE1;
  27. close FILE2;
  28. close FILE3;
复制代码
old.log FILE content

234132454594        39809871        dsoiniunlwiauwefjaopdfiasufiofps        balabala        bwrtla        balabala
234132454594        39588771                balabala        bartrbala        balabala
111111222212        12345771                balabala        bartrbala        balabala
158873235456        31267809                balabala        bartrbala        balabala


update.log FILE content

123248980898        ooireoiroeooooiqoiepqeirpoooppqe
111111222212        sadfadaeferteawteaetwetatawdfase
158873235456        dsoiniunlwiauwefjaopdfiasufiofps


result.log

234132454594        39809871        dsoiniunlwiauwefjaopdfiasufiofps        balabala        bwrtla        balabala
234132454594        39588771                balabala        bartrbala        balabala
111111222212        12345771        sadfadaeferteawteaetwetatawdfase        balabala        bartrbala        balabala
158873235456        31267809        dsoiniunlwiauwefjaopdfiasufiofps        balabala        bartrbala        balabala


[ 本帖最后由 toniz 于 2010-1-27 10:33 编辑 ]
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP