PerlでExcelのデータを操作する

Excelでデータを管理する機会は多いです。
そして、そのデータを各種のプログラム言語で操作する際には、CSVに書き出してプログラムから読み込むことがあります。
しかし、CSVを経由せずに、Excelのデータのままで読み込みできれば便利です。
そこで、PerlでExcelのデータを操作する方法を調べてみました。

1.Excel 2003までのファイルを読み込む

Excel 2003までのファイル形式(.xls)のデータを読み込むには、Spreadsheet::ParseExcelというモジュールを使います。
例えば、カレントディレクトリにある「sample.xls」というファイルを開いて、そのファイル名等の情報と、1枚目のシートのA1セルの値を表示するには、以下のようなプログラムを実行します。

use strict;
use Encode;
use Spreadsheet::ParseExcel;

# Open book file
my $filename = 'sample.xls';
my $oExcel = new Spreadsheet::ParseExcel;
my $oBook = $oExcel->Parse($filename);

# show book info
print "Filename :", encode('utf-8', $oBook->{File}) , "\n";
print "Sheet Count :", $oBook->{SheetCount} , "\n";
print "Author:", encode('utf-8',$oBook->{Author}) , "\n";

# show sheet and cell info
my $oSheet = $oBook->{Worksheet}[0];
print "Sheet Name:" , encode('utf-8', $oSheet->{Name}) , "\n";
print "A1:", encode('utf-8', $oSheet->{Cells}[0][0]->value), "\n";

1;

2.Excel 2007以降のファイルを読み込む

Excel 2007以降のファイル形式(.xlsx)のデータを読み込むには、Spreadsheet::XLSXというモジュールを使います。
Spreadsheet::XLSXは、内部的にSpreadsheet::ParseExcelを利用していて、Spreadsheet::ParseExcelとほぼ同じインターフェースで、Excel 2007以降のファイルにアクセスすることができます。
前述の例をSpreadsheet::XLSXに変えると、以下のようなプログラムになります。

use strict;
use Spreadsheet::XLSX;

# Open book file
my $filename = 'sample.xlsx';
my $oBook = Spreadsheet::XLSX->new($filename);

# show book info
print "Filename :", $oBook->{File} , "\n";
print "Sheet Count :", $oBook->{SheetCount} , "\n";
print "Author:", $oBook->{Author} , "\n";

# show sheet and cell info
my $oSheet = $oBook->{Worksheet}[0];
print "Sheet Name:" , $oSheet->{Name} , "\n";
print "A1:", $oSheet->{Cells}[0][0]->value, "\n";

ただ、Spreadsheet::XLSXは不十分なところが多いです。
上のプログラムだと、FilenameとAuthorの情報が表示されません。
また、日本語がセルに入力されている場合、「セルの値とフリガナを分離して読み込むことができない」という、致命的な問題があります。

3.XMLをパースして読み込む

Excel 2007以降のファイルは、「Office Open XML」という形式のファイルです。
Office Open XMLのファイルは、複数のXMLファイルをZipファイルに圧縮した形になっています。
それらのXMLファイルをパースすれば、中のデータを読み込むことが可能です。

Office Open XMLの仕様は、ECMA-376という規格にまとめられています。
ただし、PDFで約5,000ページにも及ぶ文書で(Excelの部分だけでも約1,000ページ)、全部を読むのはかなり大変です。