平时工作从未接触到用C++操作excel表格,直到有个研究生朋友需要爬虫网络数据需要生成excel格式的。研究后发现微软竟然没提供操作excel的接口----要么就是很麻烦(鄙视微软一分钟),从网上扒拉一圈,有个收费的项目能提供了简洁的接口---libxl.
收费就罢了,还尼玛特别贵,需要$199……免费的又被阉割了各种功能。吐槽完毕……正题:
一, 注册
如想要使用全部的功能需要付费,不想付费的只有自己去找注册机制了。去网上看一圈,52破解上有人已经破解过了,不过……想共享,收费。晕……
好消息还是有的,从上面贴出的测试注册码竟然是个有效的,省得我去研究怎么破解了。
typedef void (__cdecl * xlBookSetKeyW)(Book * handle, const wchar_t* name, const wchar_t* key);
HMODULE hdll=LoadLibraryA("libxl.dll");
xlBookSetKey=(xlBookSetKeyW)GetProcAddress(hdll, "xlBookSetKeyW");
m_book=xlCreateBook();
if(m_book)
{
(*xlBookSetKey)(m_book,L"GCCG",L"windows-282123090cc0e6036db16b60a1o3p0h9");
m_sheet=m_book->addSheet(L"Sheet1");
}
xlBookSetKeyW函数是官方提供的用来注册的函数,网上下载的免费版本里面libxl.lib 和 libxl.h中均没有该函数。好在libxl.dll中存在这个函数的定义。使用GetProcAddress获得函数的偏移。就可以使用了,把破解网站上获得的注册码复制过来,就能生成文件和表格了。感谢52破解那个哥……
二, 使用
1,读excel文件:
m_book=xlCreateBook();
m_book->load(A2W(strXlsFile.c_str()));
if(m_book)
{
m_sheet=m_book->getSheet(0);
if(m_sheet)
{
do
{
const WCHAR *wp;
wp=m_sheet->readStr(dwTmpRow++, 0);
if(!wp)
{
break;
}
vt_File.push_back(W2A(wp));
} while (dwTmpRow<7000);
}
}
m_book->release();
通过load函数把需要读的文件加载进已经建立好的book中, book::getSheet(int n)表示读那张表,下标从0开始。readStr(row, col) 读取指定的单元格。返回值是宽字符。
2, 写excel文件:
m_sheet->writeStr(0, 0, L"股东");
m_sheet->setCol(0,0,15);
m_sheet->writeStr(0, 1, L"持股比例");
m_sheet->setCol(0,1,12);
m_sheet->writeStr(0, 2, L"认缴出资额(万元)");
m_sheet->setCol(0,2,20);
m_sheet->writeStr(0, 3, L"认缴出资日期");
m_sheet->setCol(0,3,18);
m_sheet->writeStr(0, 4, L"股东类型");
m_sheet->setCol(0,4,15);
writeStr(row, col, string)用来写指定的单元格, setCol(row, col, length)用来设置指定单元格的宽度。
三,破解
注册后就能解决所有问题了吗,too naive……, 在读取文件的时候发现不论从哪儿开始读,所有的读动作都只能读取300行,这绝对是见鬼了,调试了很久最后在汇编下调试的时候进入libxl.dll,原来里面有个变量在一直自增一计数,只要大于300就会立刻返回不执行读动作。使用od打开libxl.dll找到偏移位置,把‘jle’ 改为‘jmp’ ,这下乖乖听话了……
网速太垃圾,不能把所有的都项目都上传上来,只上传修复后的dll。全部免费项目可以去官方网站下载
libxl官网
libxl.dll下载地址