使用XLSWRITE 函数时,您可以避免每次都计算 Excel 单元格范围,方法是同时指定工作表编号和范围,其中范围仅给出第一个单元格开始的位置。
如果矩阵每次迭代都改变大小,这将特别有用;我们只需取最后一个使用的单元格并将其移动矩阵的行数。
例子:
offset = 1;
for i=1:5
%# generate different size matrices each loop
A = ones(randi(4),randi(4)).*i;
%# insert matrix in Excel inside the 1st sheet, starting at cell specifed
xlswrite('filename.xls', A, 1, sprintf('A%d',offset));
%# increment offset
offset = offset + size(A,1);
end
这将创建一个包含以下内容的 Excel 文件:
1 1
1 1
1 1
2 2 2 2
3 3
3 3
4
4
4
4
5 5 5
5 5 5
5 5 5
5 5 5
请注意,每次调用 XLSWRITE 时都会与 Excel 建立连接,然后关闭。这有很大的开销。
更好的方法是打开 Excel 一次,然后重复使用同一个会话来写入所有数据,然后在完成后关闭它。但是,您必须自己调用 Office 互操作函数。
由于我上面提到的技巧现在不起作用,我将使用 "Calculate Excel Range" 函数来计算单元格范围(FEX 还有许多其他实现)。
这是代码(重复使用来自previous answer 的一些代码):
%# output file name
fName = fullfile(pwd, 'file.xls');
%# create Excel COM Server
Excel = actxserver('Excel.Application');
Excel.Visible = true;
%# delete existing file
if exist(fName, 'file'), delete(fName); end
%# create new XLS file
wb = Excel.Workbooks.Add();
wb.Sheets.Item(1).Activate();
%# iterations
offset = 0;
for i=1:50
%# generate different size matrices each loop
A = ones(randi(4),randi(4)).*i;
%# calculate cell range to fit matrix (placed below previous one)
cellRange = xlcalcrange('A1', offset,0, size(A,1),size(A,2));
offset = offset + size(A,1);
%# insert matrix in sheet
Excel.Range(cellRange).Select();
Excel.Selection.Value = num2cell(A);
end
%# save XLS file
wb.SaveAs(fName,1);
wb.Close(false);
%# close Excel
Excel.Quit();
Excel.delete();
事实上,我用 50 次迭代运行了这两个版本,并将时间与 TIC/TOC 进行了比较:
Elapsed time is 68.965848 seconds. %# calling XLSWRITE
Elapsed time is 2.221729 seconds. %# calling Excel COM directly