Qt保存Excel格式数据

2023-11-18

前言

本文以一个示例介绍了如何使用 libxlsxwriter 开源库保存QTableWidget表格中的数据到Excel文件。libxlsxwriter 是一个C语言库,可用于将文本、数字、公式和超链接写入Excel 2007以上的excel文件中的多个工作表。它支持的特性非常丰富,如合并单元格、设置字体样式、设置单元格样式、支持图标、支持各种操作系统等,这里就不一一列举了,除此之外它唯一依赖zlib库。

1、下载源码

zlib 下载地址: https://github.com/madler/zlib
libxlsxwriter 下载地址:https://github.com/jmcnamara/libxlsxwriter

2、编译源码

这里我们使用cmake 来生成vs工程进行编译。首先编译zlib,打开cmake GUI客户端,设置好zlib源码路径和构建路径,如下图所示:
在这里插入图片描述
点击 【Configure】按钮配弹出如下页面,选择vs版本及目标平台,默认是32位,这里选择64位,编译器用默认选项即可。
在这里插入图片描述
再点击【Generate】按钮生成VS工程,点击【Open Project】打开创建的vs工程,切换到Release模式,在ALL_BUILD 工程上右键生成,等待编译完成。编译结束后打开build/Release目录可以看到生成了zlib的静态库zlibstatic.lib 和 动态库zlib 、zlib.dll。如下图所示
在这里插入图片描述

接下来我们编译libxlswriter,同样用cmake生成VS工程进,在cmakeGUI中设置好libxlswriter的源码根目录及build目录后,点击【Configure】按钮,在弹出的页面中选择与编译zlib相同的配置,配置结束后会提示zlib找不到,这时需要我们手动设置zlib的两个配置项,ZLIB_INCLUDE_DIR 、ZLIB_LIBRARY_RELEASE,这里我们选择zlib的静态库,配置好之后再次点击【Configure】按钮,效果如下图所示
在这里插入图片描述
点击【Generate】按钮生成VS工程,在【解决方案】上右键选择【批生成】菜单,在弹出的页面中勾选 ALL_BUILD的Debug和Release,然后点击生成按钮,等待编译完成。注意这里xlswriter默认生成静态库
在这里插入图片描述
我遇到的问题是,在工程的属性配置中没有链接zlibstatic库,导致在使用xlswriter时报zlib中对应api符号找不到的错误,如果你也遇到类似的情况,可以在这一步手动添加zlib静态库链接,如下图所示。
在这里插入图片描述
编译完成后在build/Release目录中看到已经生成了xlswriter的静态库。如下图所示
在这里插入图片描述

3、写Excel数据示例

在Qt Creator中新建excelDemo项目,在pro目录下新建libxlswriter目录,接着创建include和lib目录,将xlsxwriter.lib和include目录下的文件拷贝到libxlswriter对应目录下,如图所示
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在pro文件中引入libxlswriter库,添加下面两行代码到pro文件中

INCLUDEPATH += $$PWD/libxlswriter/include
LIBS += -L$$PWD/libxlswriter/lib -lxlsxwriter 

在UI文件中拖拽一个QPushButton按钮和一个QTableWidget表格控件,布局如下
在这里插入图片描述
当点击保存按钮时,将表格中的数据写到excel文件中,并打开保存的excel文件,我们在cpp文件中向QTableWidget添加一些测试数据,

	void MainWindow::initTableWidget()
{
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);

    QList<QStringList> dataList;
    QStringList rowData;
    rowData << "1" << tr("20220120") << tr("张三") <<tr("18");
    dataList.append(rowData);

    rowData.clear();
    rowData << "2" << tr("20220121") << tr("李四") <<tr("19");
    dataList.append(rowData);
    rowData.clear();
    rowData << "3" << tr("20220122") << tr("王五") <<tr("19");
    dataList.append(rowData);
    rowData.clear();
    rowData << "4" << tr("20220123") << tr("赵六") <<tr("17");
    dataList.append(rowData);

    for(int i = 0; i < dataList.size(); i++)
    {
        rowData = dataList[i];
        ui->tableWidget->insertRow(i);
        for(int j = 0; j < rowData.size(); j++)
        {
            QTableWidgetItem *pItem = new QTableWidgetItem(rowData[j]);
            ui->tableWidget->setItem(i, j, pItem);
        }
    }
}

在保存按钮的响应函数中,添加代码保存数据。


void MainWindow::slot_btnClicked()
{

     QString fileName = QFileDialog::getSaveFileName(this, tr("输入保存文件名称"));
     if(fileName.isEmpty())
     {
         return;
     }

     //lxw_workbook 代表Excel文件
     lxw_workbook *pWorkBook = workbook_new(fileName.toLocal8Bit().data());
     //lxw_worksheet 代表sheet页
     lxw_worksheet *pWorkSheet = workbook_add_worksheet(pWorkBook, tr("学生信息").toUtf8().data());

     lxw_format *pHeaderFormat = workbook_add_format(pWorkBook);
     format_set_bold(pHeaderFormat);
     format_set_align(pHeaderFormat, LXW_ALIGN_CENTER);
     format_set_align(pHeaderFormat, LXW_ALIGN_VERTICAL_CENTER);
     format_set_border(pHeaderFormat, LXW_BORDER_THIN);

     int row = 0;
     for(int i = 0; i < ui->tableWidget->columnCount(); i++)
     {
         QTableWidgetItem* pHeaderItem = ui->tableWidget->horizontalHeaderItem(i);
         worksheet_write_string(pWorkSheet, row, i, pHeaderItem->text().toUtf8().data(), pHeaderFormat);
     }

     row++;
     lxw_format *pItemFormat = workbook_add_format(pWorkBook);
     format_set_align(pItemFormat, LXW_ALIGN_CENTER);
     format_set_align(pItemFormat, LXW_ALIGN_VERTICAL_CENTER);
     format_set_border(pItemFormat, LXW_BORDER_THIN);
     for(int i = 0; i < ui->tableWidget->rowCount(); i++)
     {
         for(int j = 0; j < ui->tableWidget->columnCount(); j++)
         {
             QTableWidgetItem* pItem = ui->tableWidget->item(i, j);
             worksheet_write_string(pWorkSheet, row, j, pItem->text().toUtf8().data(), pItemFormat);
         }
         row++;
     }


     lxw_error error = workbook_close(pWorkBook);
     if(error != LXW_NO_ERROR)
     {
         qDebug() << "save excel failed!";
     }

     QFileInfo fileInfo(fileName);
     QString fileDirPath = fileInfo.absoluteFilePath();
     //打开文件所在目录
     QDesktopServices::openUrl(QUrl(QString("file:///%1").arg(fileDirPath)));
     //打开保存的Excel文件
     QDesktopServices::openUrl(QUrl(QString("file:///%1").arg(fileName)));

}

从上面的代码可以看出libxlswriter的使用也是非常简单的。下面是程序运行效果,及导出的Excel文件打开后的效果。

在这里插入图片描述

在这里插入图片描述

以上就是本篇的所有内容了,关于libxlswriter的更多用法,可以自己研究学习,并不难。对以上内容有疑问的朋友,欢迎 留言讨论。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Qt保存Excel格式数据 的相关文章

  • 在 xaml 中编写嵌套类型时出现设计时错误

    我创建了一个用户控件 它接受枚举类型并将该枚举的值分配给该用户控件中的 ComboBox 控件 很简单 我在数据模板中使用此用户控件 当出现嵌套类型时 问题就来了 我使用这个符号来指定 EnumType x Type myNamespace
  • std::list 线程push_back、front、pop_front

    std list 线程安全吗 我假设不是这样 所以我添加了自己的同步机制 我认为我有正确的术语 但我仍然遇到问题 每个函数都由单独的线程调用 Thread1 不能等待 它必须尽可能快 std list
  • Excel 数字缩写格式

    这是我想要完成的任务 Value Display 1 1 11 11 111 111 1111 1 11k 11111 11 11k 111111 111 11k 1111111 1 11M 11111111 11 11M 11111111
  • 输入新行并复制上面单元格中的公式

    我正在尝试创建一个 Excel 宏来执行以下操作 在文档末尾输入新行 复制上面单元格中的公式 到目前为止我有这个 Sub New Delta Go to last cell Range A4 Select Selection End xlD
  • 如何使从 C# 调用的 C(P/invoke)代码“线程安全”

    我有一些简单的 C 代码 它使用单个全局变量 显然这不是线程安全的 所以当我使用 P invoke 从 C 中的多个线程调用它时 事情就搞砸了 如何为每个线程单独导入此函数 或使其线程安全 我尝试声明变量 declspec thread 但
  • 方程“a + bx = c + dy”的积分解

    在等式中a bx c dy 所有变量都是整数 a b c and d是已知的 我如何找到整体解决方案x and y 如果我的想法是正确的 将会有无限多个解 由最小公倍数分隔b and d 但我只需要一个解决方案 我可以计算其余的 这是一个例
  • 使用 OpenPyXL 迭代工作表和单元格,并使用包含的字符串更新单元格[重复]

    这个问题在这里已经有答案了 我想使用 OpenPyXL 来搜索工作簿 但我遇到了一些问题 希望有人可以帮助解决 以下是一些障碍 待办事项 我的工作表和单元格数量未知 我想搜索工作簿并将工作表名称放入数组中 我想循环遍历每个数组项并搜索包含特
  • 我如何以更好的方式编码而不是像这样的VBA编码

    我正在 Excel 中创建一个仪表板 但是我想知道是否有比这更好的编码方式 我想对其进行模块化 而不是这样做以使其更加整洁 Private Sub Afford If af Value True Then af afr Value Shee
  • C# 动态/expando 对象的深度/嵌套/递归合并

    我需要在 C 中 合并 2 个动态对象 我在 stackexchange 上找到的所有内容仅涵盖非递归合并 但我正在寻找能够进行递归或深度合并的东西 非常类似于jQuery 的 extend obj1 obj2 http api jquer
  • 为什么使用小于 32 位的整数?

    我总是喜欢使用最小尺寸的变量 这样效果就很好 但是如果我使用短字节整数而不是整数 并且内存是 32 位字可寻址 这真的会给我带来好处吗 编译器是否会做一些事情来增强内存使用 对于局部变量 它可能没有多大意义 但是在具有数千甚至数百万项的结构
  • 如何实例化 ODataQueryOptions

    我有一个工作 简化 ODataController用下面的方法 public class MyTypeController ODataController HttpGet EnableQuery ODataRoute myTypes pub
  • 为什么 isnormal() 说一个值是正常的,而实际上不是?

    include
  • C 函数 time() 如何处理秒的小数部分?

    The time 函数将返回自 1970 年以来的秒数 我想知道它如何对返回的秒数进行舍入 例如 对于100 4s 它会返回100还是101 有明确的定义吗 ISO C标准没有说太多 它只说time 回报 该实现对当前日历时间的最佳近似 结
  • 相当于Linux中的导入库

    在 Windows C 中 当您想要链接 DLL 时 您必须提供导入库 但是在 GNU 构建系统中 当您想要链接 so 文件 相当于 dll 时 您就不需要链接 为什么是这样 是否有等效的 Windows 导入库 注意 我不会谈论在 Win
  • 对于某些 PDF 文件,LoadIFilter() 返回 -2147467259

    我正在尝试使用 Adob e IFilter 搜索 PDF 文件 我的代码是用 C 编写的 我使用 p invoke 来获取 IFilter 的实例 DllImport query dll SetLastError true CharSet
  • 为什么 std::uint32_t 与 uint32_t 不同?

    我对 C 有点陌生 我有一个编码作业 很多文件已经完成 但我注意到 VS2012 似乎有以下语句的问题 typedef std uint32 t identifier 不过 似乎将其更改为 typedef uint32 t identifi
  • 在OpenGL中,我可以在坐标(5, 5)处精确地绘制一个像素吗?

    我所说的 5 5 正是指第五行第五列 我发现使用屏幕坐标来绘制东西非常困难 OpenGL 中的所有坐标都是相对的 通常范围从 1 0 到 1 0 为什么阻止程序员使用屏幕坐标 窗口坐标如此严重 最简单的方法可能是通过以下方式设置投影以匹配渲
  • MySQL Connector C/C API - 使用特殊字符进行查询

    我是一个 C 程序 我有一个接受域名参数的函数 void db domains query char name 使用 mysql query 我测试数据库中是否存在域名 如果不是这种情况 我插入新域名 char query 400 spri
  • 现代编译器是否优化乘以 1 和 -1

    如果我写 template
  • 如何确定 CultureInfo 实例是否支持拉丁字符

    是否可以确定是否CultureInfo http msdn microsoft com en us library system globalization cultureinfo aspx我正在使用的实例是否基于拉丁字符集 我相信你可以使

随机推荐

  • 如何让ChatGPT写情书(三步走)

    近年来 人工智能技术的迅猛发展给我们生活带来了许多便利和惊喜 而动人的情书文学也逐渐成为ChatGPT技术的应用领域之一 ChatGPT模型是一种递归神经网络 可以在大量数据的基础上为用户生成语言内容 使用GPT来写情书 相比以前的纯手工撰
  • python详细安装教程(配置环境变量)

    python安装教程 配置环境变量 人生苦短 我用python 直接在官网下载安装包 msi文件进行安装 https www python org downloads windows 下载python 注意 浏览器左下角下载 点击后 会自动
  • conda和pip 安装python依赖包区别和使用技巧

    引言 Conda 作为一种跨平台的包和虚拟环境管理器 使用的时候功能与pip类似 安装python依赖包的时候经常将两种方法混合使用 但一直没有进行具体区分其差别 重新安装python依赖包的时候出现各种不兼容的bug 经历一天烦躁的安装
  • 你不知道的 script 标签的 defer 与 async 属性

    我持续组织了近一年的源码共读活动 感兴趣的可以 点此扫码加我微信 ruochuan12 参与 每周大家一起学习200行左右的源码 共同进步 同时极力推荐订阅我写的 学习源码整体架构系列 包含20余篇源码文章 历史面试系列 另外 目前建有江西
  • 4G路由器设置

    总共分四步如下图所示 1 用网线连接电脑 2 给路由器上电 3 设置电脑网络 如图打开电脑网络和共享数据中心选中本地连接双击 弹出如下图所示弹框选择图中ipv4双击 根据下面图片配置ip地址 4 浏览器上输入地址访问路由器进行配置 第一步
  • CV 经典主干网络 (Backbone) 系列: CSP-Darknet53

    CSP Darknet53 0 引言 1 网络结构图 1 1 输入部分 1 2 CSP部分结构 1 3 输出部分 2 代码实现 2 1 代码整体实现 2 2 代码各个阶段实现 3 代码测试 4 结论 0 引言 CSP Darknet53无论
  • Halcon实战记录之二《判断两个直线或者矩形是否相交》

    项目中使用到需要判断两个矩形是否相交 由于我使用Halcon不久 对其算子还不熟悉 不知道是否有现成的算子可以直接实现 如果有 还请各位朋友给留言指出 先谢谢了 我这里用了如下的方法 1 如果两个矩形相交 那么它们中的线段一定会有相交的 我
  • LeetCode 687. 最长同值路径

    题目链接 https leetcode cn problems longest univalue path C 代码如下 Definition for a binary tree node struct TreeNode int val T
  • 优惠券的设计分享

    优惠券是一种常见的促销手段 在形式上给予消费者心理一定的折扣 然后促成订单 本文主要分享关于优惠券的设计 一 引子 促销活动的目的按对象可分为对用户 对产品 对公司 其中对用户的促销目的又可分为三种 拉新 促活 留存 优惠券作为一种常见的促
  • 前端基础知识与常见面试题(九)

    描述 现有n种砝码 重量互不相等 分别为 m1 m2 m3 mn 每种砝码对应的数量为 x1 x2 x3 xn 现在要用这些砝码去称物体的重量 放在同一侧 问能称出多少种不同的重量 注 称重重量包括 0 输入描述 对于每组测试数据 第一行
  • 逆向某联盟RSA登录

    目录 1 抓包分析 2 逆向 1 抓包分析 经典抓包套路 发现载荷password的参数进行了加密 还是如此之长 那就可以猜测是RSA加密了 点击启动器 找到login位置 然后搜索password 发现果然是RSA加密 人家还贴切的给了注
  • 零基础入门STM32编程——GPIO(五)

    系列教程链接 HAL库编程点灯篇https blog csdn net oHaoEr article details 122999523 一 GPIO简介 1 1 概述 GPIO 通用输入输出端口 即芯片的IO管脚 STM32F103系列中
  • 深度学习训练之optimizer优化器(BGD、SGD、MBGD、SGDM、NAG、AdaGrad、AdaDelta、Adam)的最全系统详解

    文章目录 1 BGD 批量梯度下降 2 SGD 随机梯度下降 2 1 SGD导致的Zigzag现象 3 MBGD 小批量梯度下降 3 1 BGD SGD MBGD的比较 4 SGDM 5 NAG 6 AdaGrad Adaptive Gra
  • EndNote在word中进行文献引用的插入时,没有出现编号问题

    转载链接 https blog csdn net qq 32120957 article details 83547621 EndNote 是一个著名的参考文献管理软件 用来创建个人参考文献库 并且可以加入文本 图像 表格和方程式等内容及链
  • 网络编程---TCP/UDP套接字编程原理

    本篇介绍的是Linux下的网络编程 故有些接口是不适用于Windows的 但是具体概念和实现方法是大体一致的 本篇重在讲解原理 具体实现请戳这里 gt UDP套接字编程实现 介绍 网络编程套接字 socket 也是进程间通信的一种方式 但是
  • 浅谈Canvas和SVG的区别

    各位都知道canvas是html5提供的新元素 而svg存在的历史要比canvas久远 已经有十几年了 svg并不是html5专有的标签 Canvas和SVG的区别在哪呢 那我们就看看它们的特点 1 SVG SVG可缩放矢量图形 Scala
  • 基于卷积神经网络的人脸表情识别综述

    基于卷积神经网络的人脸表情识别 摘要 在日常的沟通与交流过程中 运用面部表情可以促使沟通交流变得更加顺畅 因此对于人类而言 进行面部表情的解读也是进行相关沟通交流内容获取的重要程序 随着科学技术的不断发展 人工智能在日常人类交流沟通中 运用
  • Jenkins+Python完整版

    一 简介 一般网站部署的流程 这边是完整流程而不是简化的流程 需求分析 原型设计 开发代码 内网部署 提交测试 确认上线 备份数据 外网更新 最终测试 如果发现外网部署的代码有异常 需要及时回滚 一般是运维来做 功能测试 上线的时间 jen
  • 北京的IT崩盘了么?

    相信今年的互联网行情 大家都有目共睹 身边被各种裁员 劝退的朋友比往年要多了很多 而如今想要找一份还不错的工作 难度也是直线上升 我个人的感受是 这行情就像股价 有起有落 目前处于衰退期 崩盘倒是不至于 网上对此也有很多看法 今天分享一些
  • Qt保存Excel格式数据

    目录 前言 1 下载源码 2 编译源码 3 写Excel数据示例 前言 本文以一个示例介绍了如何使用 libxlsxwriter 开源库保存QTableWidget表格中的数据到Excel文件 libxlsxwriter 是一个C语言库 可