读取excel文件(使用perl处理)

来源:互联网 发布:淘宝网粉色连衣裙 编辑:程序博客网 时间:2024/05/17 00:06

做了一个简单的处理excel文件的perl程序,批量读取其中的数据将其转换csv文件

代码如下:

#!/usr/local/bin/perl##########################################xlstocsv ver 0.2 !                     ##xls文件转换csv                         ##作者:昨夜星尘                         ##                                       ##Mail:                                  ##########################################use strict;use warnings;use Spreadsheet::ParseExcel;use Spreadsheet::ParseExcel::FmtUnicode;sub parse_excel{    #读取xls文件内容    #参数: xls文件名,每行处理函数(可省)sub(@)    my($filename,$do_fuc);    if(ref($_[0]) eq 'CODE') {        $do_fuc = $_[0];        $filename = $_[1];    } else {        $do_fuc = $_[1];        $filename = $_[0];    }    return unless $filename||(ref($do_fuc) eq 'CODE');    my $Excel = new Spreadsheet::ParseExcel;    my $code = "CP936"; #gb support    my $FmtGBK = Spreadsheet::ParseExcel::FmtUnicode->new(Unicode_Map => $code); #gb support    my $Book = $Excel->Parse($filename, $FmtGBK);    my($iMaxRow,$iMaxCol,@cols);    EWSFOR: foreach my$WorkSheet (@{$Book->{Worksheet}}) {        if( defined $WorkSheet->{MaxRow} ) {            $iMaxRow = $WorkSheet->{MaxRow};        } else {            next EWSFOR;        }        ERFOR: for(my $iR = $WorkSheet->{MinRow}; $iR <= $iMaxRow; $iR++) {            if( defined $WorkSheet->{MaxCol} ) {                $iMaxCol = $WorkSheet->{MaxCol}            } else {                next ERFOR;            }            $#cols = -1;            ECFOR: for(my $iC = $WorkSheet->{MinCol}; $iC <= $iMaxCol; $iC++) {                my $Cell = $WorkSheet->{Cells}[$iR][$iC];                if($Cell) {                    push @cols, $Cell->Value;                } else {                    push @cols, "";                }            }            if( $do_fuc ) {                &{$do_fuc}(@cols);            } else {                print join(',',@cols),"\n";            }        }    }}my (@xlsformats,$ttindex,$defindex);sub readxlsformat($){    #读入xls格式文件    #参数: xls格式文件(是一个csv文件)    open XFS, "<$_[0]" or die "读取xls格式文件$_[0]失败: $!";    $#xlsformats=-1;    ($ttindex,$defindex) = (-1,-1);    while(<XFS>) {        next if /^\s*$/;        my @rs=split /:/;        $rs[0] =~ s/^\s+//g;        $rs[0] =~ s/\s+$//g;        next if !defined($rs[1])||$rs[1]=~/^\s*$/;        my @ri=split /,/,$rs[1];        foreach (@ri) {            s/^\s+//g;            s/\s+$//g;        }        push @xlsformats, [$rs[0],@ri];        $ttindex  = $#xlsformats if ($ttindex < 0)&&($rs[0] eq '#');        $defindex = $#xlsformats if ($defindex < 0)&&($rs[0] eq '*');    }    close XFS;    $ttindex = $defindex if $ttindex < 0;    die "没有格式标题!" if $ttindex < 0;}sub cvtxlstocsv(@){    #将xls文件转为csv文件,csv文件名位xls文件名变后缀    #参数: xls文件列表    foreach my$xlsfile(@_) {        next unless -e $xlsfile;        my $csvfile = $xlsfile;        $csvfile =~ s/(?:\..{0,3})$/\.csv/i;        open TOCSV, ">$csvfile" or die "打开文件$csvfile失败: $!";        parse_excel $xlsfile, sub {            print TOCSV join(',',@_),"\n";        };        close TOCSV;    }}sub writetocsv($@) {    #将所有的xls文件内容传入csv文件中    #参数: csv文件名,xls文件列表    my $csvfile = shift;    my $oldcsvfmt = "";    open CSVFILE, ">$csvfile" or die "打开${csvfile}文件失败: $!";    print CSVFILE join(',',@{$xlsformats[$ttindex]}[1..$#{$xlsformats[$ttindex]}]),"\n";    foreach my$xlsfile(@_) {        next unless -e $xlsfile;        my$index=-1;        foreach my$i(0..$#xlsformats) {            do{$index=$i;last;}if $xlsformats[$i][0] eq $xlsfile;        }        $index = $defindex if $index < 0;        die "找不到对应xls文件格式" if $index < 0;        my$ttl=0;        parse_excel $xlsfile, sub {            unless($ttl) {                my@fi = (-1) x $#{$xlsformats[$index]};                my%xi = ();                my$i = 0;                foreach (@_) {                    $xi{$_} = $i if $_;                    $i++;                }                foreach $i(0..$#fi) {                    $fi[$i] = $xi{$xlsformats[$index][$i+1]} if defined $xi{$xlsformats[$index][$i+1]};                }                my$csvformat = "format CSVFILE=\n" . '@*,' x ($#fi+1);                $csvformat =~ s/,$/\n/;                foreach (@fi) {                    if($_ < 0) {                        $csvformat .= '"",';                    } else {                        $csvformat .= "\$_[$_],"                    }                }                $csvformat =~ s/,$/\n\.\n/;                if($oldcsvfmt ne $csvformat) {                    no warnings 'redefine';                    eval $csvformat;                    $oldcsvfmt = $csvformat;                };                $ttl++;            } else {                write CSVFILE;            }        };    }    close CSVFILE;}my@extfs=();my($fmtfl,$outfl)=("","");{    my$argsta=0;    CHECKARG: foreach (@ARGV) {        #选择输出文件        do{$argsta=1;  next CHECKARG;} if /^-o$/;        #选择格式文件        do{$argsta=2;  next CHECKARG;} if /^-f$/;        #帮助        do{$argsta=-1; last CHECKARG;} if /^-\?/;        SWITCH: {            $argsta == 0 && do{push @extfs,$_;last SWITCH;};            $argsta == 1 && do{$outfl=$_;$argsta=0;last SWITCH;};            $argsta == 2 && do{$fmtfl=$_;$argsta=0;last SWITCH;};        }    }    if($argsta < 0) {        print <<'HELPINFO';    使用说明:        xlstocsv.pl <文件> ... [参数 <文件>] [-?]        <文件>为需要转换的xls文件,可以使用*和?作为扩展。没有定义参数文件        的时候,将xls文件直接转换为后缀名为.csv的csv文件。    参数:       -f <文件>  : 使用<文件>中的格式转换xls文件。       -o <文件>  : 使用<文件>作为xls文件转换的输出文件。       -?         : 显示帮助信息。HELPINFO        exit;    }    unless(@extfs) {        print "请输入转换Excel文件名: ";        my$if = <STDIN>;        chomp $if;        push @extfs,$if;    }}my @xlsfiles=sort glob join(' ',@extfs);#删除顺序序列中的重复值{    my$prexls="";    my($p1,$p2) = (0,0);    while($p1<=$#xlsfiles) {        if($prexls ne $xlsfiles[$p1]) {            if($p1>$p2) {                $xlsfiles[$p2] = $xlsfiles[$p1];            }            $prexls=$xlsfiles[$p2];            $p2++;        }    } continue {        $p1++;    }    $#xlsfiles=$p2-1;}if($fmtfl) {    $outfl = '-' unless $outfl;    readxlsformat $fmtfl;    writetocsv $outfl,@xlsfiles;} else {    if($outfl) {        print "请输入格式文件!";    } else {        cvtxlstocsv @xlsfiles;    }}


原创粉丝点击