- UID
- 2
- 精华
- 积分
- 7736
- 威望
- 点
- 宅币
- 个
- 贡献
- 次
- 宅之契约
- 份
- 最后登录
- 1970-1-1
- 在线时间
- 小时
|
学过正则表达式以后,是觉得有一些神奇的用途,不过今天这一次却是解决了我一个实际问题,那就是,如何统计递归目录(也就是包含任意级子目录)里的代码量。
情况是这样的,老板让写软件著作权登记,我们保密检查工具前年就开始做的,代码文件多了去了,但是登记申请表中要填写一个源程序量,也就是代码行数。对于这个由于代码过多,一般方法实在不好统计,如果用c实现也会比较麻烦,预计代码量也会在300行以上。最近两天刚巧学了perl,这个脚本语言主要用于文本处理和系统shell事务的处理,而且能力比较强。
提出问题:C:\temp\HyTramSerial\HyTramSerial下文件类型丛杂,一般只能模糊统计,也就是计算所有h和cpp的总大小,然后根据每行均值粗略统计出该有多少行。目录结构在文章最底部贴出。
现在用perl的find2perl功能进行递归目录查找,也就是给定一个父目录,其任何子目录以及子目录的子目录都会进行查找,书上讲的很模糊,我自己花了1小时研究了一下,最终有了结果。perl的bin目录下有find2perl,你给他传递目录和筛选文件类型和排除文件这类参数以后,他可以动态生成perl代码。其中筛选文件类型和排除文件都是可以用正则表达式的,这就十分强大了。此外,find2perl的功能几乎和linux的find命令一样,可设置的参数极多。不过我仅仅需要指定一个初始父目录,一个目的文件类型即可。因此命令如下:"E:\strawberry\perl\bin\find2perl.bat" "C:\temp\HyTramSerial\HyTramSerial" -name "*.cpp|*.h" 得到的代码如下:- #! E:\strawberry\perl\bin\perl.exe -w
- eval 'exec E:\strawberry\perl\bin\perl.exe -S $0 ${1+"[email=$@%22%7D%27]$@"}'[/email]
- if 0; #$running_under_some_shell
- use strict;
- use File::Find ();
- # Set the variable $File::Find::dont_use_nlink if you're using AFS,
- # since AFS cheats.
- # for the convenience of &wanted calls, including -eval statements:
- use vars qw/*name *dir *prune/;
- *name = *File::Find::name;
- *dir = *File::Find::dir;
- *prune = *File::Find::prune;
- sub wanted;
-
- # Traverse desired filesystems
- File::Find::find({wanted => \&wanted}, 'C:\\temp\\HyTramSerial\\HyTramSerial');
- exit;
- sub wanted {
- /^.*\.cpp|.*\.h\z/s && print("$name\n");
- }
复制代码 因为要统计行数,修改结果如下:(顺便也统计了一下字数和文件数)- use File::Find ();
- use vars qw/*name *dir *prune/;
- *name = *File::Find::name;
- *dir = *File::Find::dir;
- *prune = *File::Find::prune;
- my(@array)=();
- sub wanted
- {
- /^.*\.cpp|.*\.h\z/s &&(push @array,$name);
- }
- File::Find::find({wanted => \&wanted}, 'C:\\temp\\HyTramSerial\\HyTramSerial');
- @ARGV=@array;
- print "total file num=$#array\n";
- my($lines)=0;
- my($wordnum)=0;
- while(<>)
- {
- $wordnum += length $_;
- $lines++;
- }
- print "total lines=$lines\n";
- print "total wordnum=$wordnum\n";
复制代码 得到结果是十分迅速的,3秒就好了,我觉得如果用c也得需要几秒。。。
结果如下:
|
|