libxlsxwriter簇状柱形图绘制

news2024/11/24 12:55:25

libxlsxwriter的功能覆盖面很大,今天一起来看一下如何用这个库来生成带有簇状柱形图的表格。

1 簇形柱状图

首先来看一下Excel的样例表格,簇状柱形图往往是用来对比若干“系列”的数据在某一时间段内,或某一情境下的差异情况。在商务领域还是非常常见的。

在这里插入图片描述

对于人工智能领域的程序员来说,往往更熟悉的簇状柱形图是核弹厂的性能对比图:
在这里插入图片描述

题外话题外话~

这种图表相信大多数人已经非常熟悉。这里就不多说了。它的几个要素为:

  • 系列
  • 柱形
  • 成簇

2 代码示例及详解

二话不说,先上代码。

#include "xlsxwriter.h"
#include <iostream>
#include <wchar.h>
#include <windows.h>

using std::string;

string GBKToUTF8(const char* strGBK)
{
	int len = MultiByteToWideChar(CP_ACP, 0, strGBK, -1, NULL, 0);
	wchar_t* wstr = new wchar_t[len + 1];
	memset(wstr, 0, len + 1);
	MultiByteToWideChar(CP_ACP, 0, strGBK, -1, wstr, len);
	len = WideCharToMultiByte(CP_UTF8, 0, wstr, -1, NULL, 0, NULL, NULL);
	char* str = new char[len + 1];
	memset(str, 0, len + 1);
	WideCharToMultiByte(CP_UTF8, 0, wstr, -1, str, len, NULL, NULL);
	string strTemp = str;
	if (wstr) delete[] wstr;
	if (str) delete[] str;
	return strTemp;
}

/* 向worksheet中写入一些数据. */
void write_worksheet_data(lxw_worksheet* worksheet) {

    uint8_t data[5][3] = {
        /* 三列数据. */
        {1,   2,   3},
        {2,   4,   6},
        {3,   6,   9},
        {4,   8,  12},
        {5,  10,  15}
    };

    int row, col;

    worksheet_write_string(worksheet, 0, 0, GBKToUTF8("2018年").data(), NULL);                     
	worksheet_write_string(worksheet, 1, 0, GBKToUTF8("2019年").data(), NULL);
	worksheet_write_string(worksheet, 2, 0, GBKToUTF8("2020年").data(), NULL);
    worksheet_write_string(worksheet, 3, 0, GBKToUTF8("2021年").data(), NULL);
    worksheet_write_string(worksheet, 4, 0, GBKToUTF8("2022年").data(), NULL);

    for (row = 0; row < 5; row++)
    {
        for (col = 1; col < 4; col++)
        {
            worksheet_write_number(worksheet, row, col, data[row][col-1], NULL);
        }
    }
}

/* 创建一个带有图表的表格文件. */
int main(int argc, char* argv[]) 
{
    lxw_workbook* workbook = workbook_new(GBKToUTF8("簇状柱形图示例.xlsx").data());                           
    lxw_worksheet* worksheet = workbook_add_worksheet(workbook, NULL);

    /* 向表格中写入一些数据. */
    write_worksheet_data(worksheet);

    /* 创建一个图表对象. */
    lxw_chart* chart = workbook_add_chart(workbook, LXW_CHART_COLUMN);

    // 指定表格,在最简单的例子中我们添加一些数据系列,空的系列种类将默认为1到5
    // 若非空指定数据系列的名称,则可以按照索引列进行指定。
	lxw_chart_series* series1 = chart_add_series(chart, "=Sheet1!$A$1:$A$5", "=Sheet1!$B$1:$B$5");
	lxw_chart_series* series2 = chart_add_series(chart, NULL, "=Sheet1!$C$1:$C$5");
	lxw_chart_series* series3 = chart_add_series(chart, NULL, "=Sheet1!$D$1:$D$5");

    chart_series_set_categories(series1, "Sheet1", 0, 0, 4, 0);
    chart_series_set_categories(series2, "Sheet1", 0, 0, 4, 0);
    chart_series_set_categories(series3, "Sheet1", 0, 0, 4, 0);

    // 给表格添加系列名称
	chart_series_set_name(series1, GBKToUTF8("青菜").data());
	chart_series_set_name(series2, GBKToUTF8("萝卜").data());
	chart_series_set_name(series3, GBKToUTF8("鸡蛋").data());

    // 给表头文字设置格式
    lxw_chart_font font;
    font.bold = LXW_EXPLICIT_FALSE;
    font.color = LXW_COLOR_GREEN;

    chart_title_set_name(chart, GBKToUTF8("年终销售情况").data());
    chart_title_set_name_font(chart, &font);

    // 给坐标轴添加名称
    chart_axis_set_name(chart->x_axis, GBKToUTF8("年份").data());
    chart_axis_set_name(chart->y_axis, GBKToUTF8("万吨").data());

    /* 向worksheet中插入图表. */
    worksheet_insert_chart(worksheet, CELL("B7"), chart);

    return workbook_close(workbook);
}

小白这里的代码还是延续了这个系列文章的一贯风格,即将中文使用添加进了例程之中。以上例程改编自libxlsxwriter官网的例程chart.c。

以上程序生成一个名为簇状柱形图示例.xlsx的表格。最终内容呈现如下图所示:
在这里插入图片描述

重点需要说明的是:

系列,即图中横坐标上的2018年~2022年,有两种方式进行插入

  • chart_add_series(chart, "=Sheet1!$A$1:$A$5", "=Sheet1!$B$1:$B$5");这种方式中第二个参数指定了系列数据的来源是A1到A5单元格;
  • chart_series_set_categories(series1, "Sheet1", 0, 0, 4, 0);这种方式通过坐标指定(0,0)到(0,4)单元格为系列的数据来源。

chart_series_set_name(series1, GBKToUTF8("青菜").data());通过这种方式给系列指定名称。

chart_axis_set_name(chart->x_axis, GBKToUTF8("年份").data());通过这种方式来给坐标轴插入标题;

worksheet_insert_chart(worksheet, CELL("B7"), chart); 通过这种方式来将图表插入到表格中的指定位置(图片的左上角插入到对应的单元格,此例中插入到B7)。

看似简单,实际上,确实也不难。注意消化掉这个例程就好。还有一些其他的表格相关的指定功能这里可能没涉及到,在以后的博客文章中可能慢慢涉及。
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/373934.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

小白量化《穿云箭集群量化》(4)指标公式写策略

小白量化《穿云箭集群量化》&#xff08;4&#xff09;指标公式写策略 穿云箭量化平台支持中文Python写量化策略&#xff0c;同时也直接支持股票公式指标写策略。下面我们看看是如何实现的。 股票软件的指标公式语法是一样的&#xff0c;不同仅仅是个别函数或绘图函数或绘图命令…

java多态理解和底层实现原理剖析

java多态理解和底层实现原理剖析多态怎么理解java中方法调用指令invokespecial和invokevirtual指令的区别invokeinterface指令方法表接口方法调用为什么不能利用方法表快速定位小结多态怎么理解 抽象事务的多种具体表现&#xff0c;称为事务的多态性。我们在编码过程中通常都是…

计算机网络 第4章 作业1

一、选择题 1. 由网络层负责差错控制与流量控制,使分组按序被递交的传输方式是_________&#xff08;C&#xff09; A&#xff0e;电路交换 B&#xff0e;报文交换 C&#xff0e;基于虚电路的分组交换 D&#xff0e;基于数据报的分组交换 2. TCP/IP 参考…

Bunifu.UI.WinForms 6.0.2 Crack

Bunifu.UI.WinForms为 WinForms创建令人惊叹的UI Bunifu.UI.WinForms我们为您提供了现代化的快速用户界面控件。用于 WinForms C# 和 VB.NET 应用程序开发的完美 UI 工具 简单 Bunifu.UI.WinForms没有臃肿的特征。正是您构建令人惊叹的 WinForms 应用程序所需要的。只需拖放然…

计算机网络高频知识点

目录 一、http状态码 二、强缓存与协商缓存 三、简单请求与复杂请求 四、PUT 请求类型 五、GET请求类型 六、GET 和 POST 的区别 七、跨域 1、什么时候会跨域 2、解决方式 八、计算机网络的七层协议与五层协议分别指的是什么 1、七层协议 2、五层协议 九、计算机网…

监控生产环境中的机器学习模型

简介 一旦您将机器学习模型部署到生产环境中&#xff0c;很快就会发现工作还没有结束。 在许多方面&#xff0c;旅程才刚刚开始。你怎么知道你的模型的行为是否符合你的预期&#xff1f;下周/月/年&#xff0c;当客户&#xff08;或欺诈者&#xff09;行为发生变化并且您的训练…

服务器部署—部署springboot之Linux服务器安装jdk和tomcat【建议收藏】

我是用的xshell连接的云服务器&#xff0c;今天想在服务器上面部署一个前后端分离【springbootvue】项目&#xff0c;打开我的云服务器才发现&#xff0c;过期了&#xff0c;然后又买了一个&#xff0c;里面环境啥都没有&#xff0c;正好出一期教程&#xff0c;方便大家也方便自…

大数据框架之Hadoop:MapReduce(三)MapReduce框架原理——ReduceTask工作机制

1、ReduceTask工作机制 ReduceTask工作机制&#xff0c;如下图所示。 &#xff08;1&#xff09;Copy阶段&#xff1a;ReduceTask从各个MapTask上远程拷贝一片数据&#xff0c;并针对某一片数据&#xff0c;如果其大小超过一定阈值&#xff0c;则写到磁盘上&#xff0c;否则直…

DHTMLX Suite 8.0.0 Crack

适用于现代 Web 应用程序的强大 JavaScript 小部件库 - DHTMLX 套件 用于创建现代用户界面的轻量级、快速且通用的 JavaScript/HTML5 UI 小部件库。 DHTMLX Suite 有助于推进 Web 开发和构建具有丰富功能的数据密集型应用程序。 DHTMLX Suite 是一个 UI 小部件库&#xff0c;用…

指针数组和数组指针的区别

数组指针&#xff08;也称行指针&#xff09;定义 int (*p)[n];()优先级高&#xff0c;首先说明p是一个指针&#xff0c;指向一个整型的一维数组&#xff0c;这个一维数组的长度是n&#xff0c;也可以说是p的步长。也就是说执行p1时&#xff0c;p要跨过n个整型数据的长度。如要…

【前端】JavaScript构造函数

文章目录概念执行过程返回值原型与constructor继承方式原型链其他继承方式&#xff08;还没写&#xff09;参考概念 在JS中&#xff0c;通过new来实例化对象的函数叫构造函数。实例化对象&#xff0c;也就是初始化一个实例对象。构造函数一般首字母大写。 构造函数的目的&…

Android性能调优 - 启动优化

一、APP启动优化1、 你对 APP 的启动有过研究吗? 有做过相关的启动优化吗?程序员&#xff1a;之前做项目的时候&#xff0c;我发现程序在冷启动时&#xff0c;会有 1s 左右的白屏闪现&#xff0c;低版本是黑屏的现象&#xff0c;在这期间我通过翻阅系统主题源码&#xff0c;发…

26 openEuler管理网络-使用ip命令配置网络

文章目录26 openEuler管理网络-使用ip命令配置网络26.1 配置IP地址26.1.1 配置静态地址26.1.2 配置多个地址26.2 配置静态路由26 openEuler管理网络-使用ip命令配置网络 说明&#xff1a; 使用ip命令配置的网络配置可以立即生效但系统重启后配置会丢失。 26.1 配置IP地址 使用…

JVM - G1垃圾收集器深入剖析

​​​​​​​1、G1收集器概述 HotSpot团队一直努力朝着高效收集、减少停顿(STW: Stop The World)的方向努力&#xff0c;也贡献了从串行Serial收集器、到并行收集器Parallerl收集器&#xff0c;再到CMS并发收集器&#xff0c;乃至如今的G1在内的一系列优秀的垃圾收集器。 G…

ER图、ERD图

ER图、ERD图1. 什么是ERD1.1 举例2. ERD符号指南2.1 实体2.2 属性2.3 主键2.4 外键2.4 关系2.5 基数2.5.1 一对一的基数的例子2.5.2 一对多的基数的例子2.5.3 多对多的基数的例子3.概念、逻辑和物理数据模型3.1 概念数据模型3.2 逻辑数据模型3.3 物理数据模型4.如何绘制ER图?5…

python的装饰器与设计模式中的装饰器模式

相信很多人在初次接触python中的装饰器时&#xff0c;会跟我一样有个疑问&#xff0c;这跟设计模式中的装饰器模式有什么区别吗&#xff1f;本质上是一样的&#xff0c;都是对现有对象&#xff0c;包括函数或者类的一种扩展。这篇文档将进行对比分析。 python的装饰器 装饰器…

Acwing 蓝桥杯 第一章 递归与递推

我上周在干什么&#xff0c;感觉我上周啥也没训&#xff0c;本来两天一次的vp也没v很寄啊&#xff0c;再这样下去真不行了先总结一下如何爆搜&#xff1a;先去确定好枚举的对象枚举的对象很重要&#xff01;&#xff01;这直接影响了复杂度然后就是去想递归树就好了一、确定状态…

基于VSG的预同步并离网控制MATLAB仿真模型

MATLAB2019b主要模块&#xff1a;并网逆变器VSG控制预同步控制电流电流双环控制锁相环、三相准PR控制、PWM0.65秒开始并网运行&#xff01;&#xff01;&#xff01;仿真模型&#xff1a;逆变器输出电压、电流波形。电压为单相&#xff08;可观察相位情况&#xff09;&#xff…

【逐步剖C】-第八章-指针进阶-下

前言&#xff1a;在文章【逐步剖C】-第八章-指针进阶-上与指针初阶中我们介绍了有关指针较为全面的知识&#xff0c;本篇文章主要从指针和数组相关试题出发&#xff0c;进一步巩固对指针的学习。接下来&#xff0c;让我们开始吧。 一、“真假”数组名 前言&#xff1a;这一部…

【每日一题】集合汇总 集合面试题

集合前言&#xff1a;图片一、集合分类1、实现 Collection 接口2、实现 Map 接口二、实现类定义1、ArrayList&#xff08;非线程安全&#xff09;2、LinkedList&#xff08;非线程安全&#xff09;3、HashSet&#xff08;非线程安全&#xff09;4、TreeSet&#xff08;非线程安…