免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: woodie
打印 上一主题 下一主题

[原创]perl在编辑巨大文件时的应用 [复制链接]

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
21 [报告]
发表于 2006-07-26 10:23 |只看该作者
原帖由 waker 于 2006-7-26 10:17 发表
是的
: >&3已经完成了对文件的操作

exec 3<&-与exec 3>&-都无所谓吧?它只是释放FD表项而已

你说得没错,我那么写只是为了便于理解。^_^

论坛徽章:
7
荣誉版主
日期:2011-11-23 16:44:17子鼠
日期:2014-07-24 15:38:07狮子座
日期:2014-07-24 11:00:54巨蟹座
日期:2014-07-21 19:03:10双子座
日期:2014-05-22 12:00:09卯兔
日期:2014-05-08 19:43:17卯兔
日期:2014-08-22 13:39:09
22 [报告]
发表于 2006-07-26 11:09 |只看该作者
不知道开始怎么试的,waker的方法很正确,可是现在怎么试结果都是最后的部分没有截断。

论坛徽章:
7
荣誉版主
日期:2011-11-23 16:44:17子鼠
日期:2014-07-24 15:38:07狮子座
日期:2014-07-24 11:00:54巨蟹座
日期:2014-07-21 19:03:10双子座
日期:2014-05-22 12:00:09卯兔
日期:2014-05-08 19:43:17卯兔
日期:2014-08-22 13:39:09
23 [报告]
发表于 2006-07-26 11:23 |只看该作者
又改进了一下
  1. { off=$(($(find file -printf "%s")-$(head -10|wc -c))); dd of=file conv=notrunc bs=32k; :|dd of=file obs=$off seek=1; } <file
复制代码

论坛徽章:
7
荣誉版主
日期:2011-11-23 16:44:17子鼠
日期:2014-07-24 15:38:07狮子座
日期:2014-07-24 11:00:54巨蟹座
日期:2014-07-21 19:03:10双子座
日期:2014-05-22 12:00:09卯兔
日期:2014-05-08 19:43:17卯兔
日期:2014-08-22 13:39:09
24 [报告]
发表于 2006-07-26 11:33 |只看该作者
去掉也应该没问题
  1. { off=$(($(find file -printf "%s")-$(head -10|wc -c))); dd of=file conv=notrunc bs=32k; dd of=file obs=$off seek=1; } <file
复制代码


这里没有用wc取文件尺寸,是因为效率问题,用ls也可以做到。理想情况就是如waker的代码那样根本不用取size,可是不知为什么总是未测试通过,难道我第一次测试看错了?

论坛徽章:
8
摩羯座
日期:2014-11-26 18:59:452015亚冠之浦和红钻
日期:2015-06-23 19:10:532015亚冠之西悉尼流浪者
日期:2015-08-21 08:40:5815-16赛季CBA联赛之山东
日期:2016-01-31 18:25:0515-16赛季CBA联赛之四川
日期:2016-02-16 16:08:30程序设计版块每日发帖之星
日期:2016-06-29 06:20:002017金鸡报晓
日期:2017-01-10 15:19:5615-16赛季CBA联赛之佛山
日期:2017-02-27 20:41:19
25 [报告]
发表于 2006-07-26 11:40 |只看该作者
俺的应该是错的,再考虑一下,先吃饭

论坛徽章:
8
摩羯座
日期:2014-11-26 18:59:452015亚冠之浦和红钻
日期:2015-06-23 19:10:532015亚冠之西悉尼流浪者
日期:2015-08-21 08:40:5815-16赛季CBA联赛之山东
日期:2016-01-31 18:25:0515-16赛季CBA联赛之四川
日期:2016-02-16 16:08:30程序设计版块每日发帖之星
日期:2016-06-29 06:20:002017金鸡报晓
日期:2017-01-10 15:19:5615-16赛季CBA联赛之佛山
日期:2017-02-27 20:41:19
26 [报告]
发表于 2006-07-26 13:21 |只看该作者
饭吃饱了,问题没有解决

论坛徽章:
7
荣誉版主
日期:2011-11-23 16:44:17子鼠
日期:2014-07-24 15:38:07狮子座
日期:2014-07-24 11:00:54巨蟹座
日期:2014-07-21 19:03:10双子座
日期:2014-05-22 12:00:09卯兔
日期:2014-05-08 19:43:17卯兔
日期:2014-08-22 13:39:09
27 [报告]
发表于 2006-07-26 13:32 |只看该作者
看看perl的这句
truncate( W, tell(W) );
多爽

who TELL me? 可爱的dd,它就在那,它就是不告诉你

论坛徽章:
7
荣誉版主
日期:2011-11-23 16:44:17子鼠
日期:2014-07-24 15:38:07狮子座
日期:2014-07-24 11:00:54巨蟹座
日期:2014-07-21 19:03:10双子座
日期:2014-05-22 12:00:09卯兔
日期:2014-05-08 19:43:17卯兔
日期:2014-08-22 13:39:09
28 [报告]
发表于 2006-07-26 15:16 |只看该作者
这个有趣,刚试出来的,好像exec n<>file 和 exec n>file不同,在写文件时一个截断为0,一个不截断.

  1. { off=$(($(find file -printf "%s")-$(head -10|wc -c))); cat ; dd of=file obs=$off seek=1; } <file 1<>file
复制代码

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
29 [报告]
发表于 2006-07-26 16:39 |只看该作者
按flw的思路,仿照perl的rename工具,用perl写了一个简陋的wraper用来在大文件中删除一些行,可以方便简单地调用:
  1. $ cat pdel
  2. #!/usr/bin/perl
  3. die "Usage: $0 perl-condition file\n" if $#ARGV != 1;
  4. $cmd = "print W unless ".$ARGV[0];
  5. $file = $ARGV[1];
  6. open R, "<$file" or die "Cannot open file ".$file." to read";
  7. open W, "+<$file" or die "Cannot open file ".$file." to write";
  8. while(<R>){
  9.     eval $cmd;
  10. }
  11. truncate( W, tell(W) );
复制代码

调用方法:
pdel 删除条件 文件名
如删除前10行:
pdel '$. <= 10' file
删除#打头的行:
pdel '/^#/' file
删除空行:
pdel '/^$/' file

[ 本帖最后由 woodie 于 2006-7-26 17:26 编辑 ]

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
30 [报告]
发表于 2006-07-26 18:26 |只看该作者
可惜,29楼的代码在循环中调用eval,会导致性能急剧下降,还得另想办法。
  1. #!/usr/bin/perl
  2. die "Usage: $0 perl-condition file\n" if $#ARGV != 1;
  3. $cmd = "print W unless ".$ARGV[0];
  4. $file = $ARGV[1];
  5. open FH, ">pdel.tmp" or die "Error write script file";
  6. print FH q[
  7. open R, "<].$file.q[" or die "Cannot open file ].$file.q[ to read";
  8. open W, "+<].$file.q[" or die "Cannot open file ].$file.q[ to write";
  9. while(<R>){
  10.     ].$cmd.q[;
  11. }
  12. truncate( W, tell(W) );];
  13. if ( system "perl pdel.tmp" )
  14.     { die "Error execute script"};
  15. unlink "pdel.tmp";
复制代码


上面的代码用了一个临时文件,笨办法。
性能应该没有问题了,用法不变。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP