用 Python 画如此漂亮的插图 ,So easy

news2024/11/15 14:01:12

人生苦短,快学Python!

今天我们进行一次实战案例分享,以全球预期寿命与人均 GPD数据为例,写一篇 Python 中漂亮散点图的快速指南。除了正常的数据清洗/处理、还会进行简单的统计分析,实现数据处理-统计分析-可视化一条龙。

你会发现,用 Python 画如此漂亮的专业插图 ,So easy!

数据处理

所用数据:全球预期寿命与人均 GPD数据(已校正通货膨胀和跨国价格差异)

数据来源:https://ourworldindata.org/

本文所用数据和代码已打包,获取方式见文末。

导入数据:

import pandas as pd

expectancy_data = pd.read_csv("life-expectancy-vs-gdp-per-capita.csv")

# 为方便起见,重命名列
expectancy_data.rename(columns={"Entity":"Country", 
                                "Life expectancy at birth (historical)": "Expectancy",
                                "GDP per capita": "GDP", 
                                "Population (historical estimates)": "Population"}, inplace=True)
expectancy_data

输出:

该数据表中的最新数据是2021年,但由于“均国内生产总值”这列数据只有道2018年的,所以我们本文便以2018年的数据为基础进行分析和可视化。同时,由于我们无法对缺失值进行分析,注意删除缺失值。

GDP_data = expectancy_data[~expectancy_data["GDP"].isna()]
GDP_data = GDP_data[GDP_data["Year"] == 2018]
GDP_data = GDP_data[GDP_data["Country"] != "World"]
GDP_data

输出:

这样我们便完成了最基本的数据处理工作。

可视化

今天的可视化还会用到seaborn,它是一个调用 matplotlib 的统计绘图库

(https://github.com/mwaskom/seaborn)

导入所需Python库:

import numpy as np 
import seaborn as sns
import matplotlib.pyplot as plt 
from matplotlib.lines import Line2D
import matplotlib.patches as mpatches

sns.set_style('darkgrid', {'font.sans-serif': ['simhei','FangSong']})

注意,上述代码最后一行是为了解决中文乱码。

接下来我们便可以使用Matplotlib+seaborn制作漂亮的散点图,其中重要的一步是我们将Population列缩放一百万倍并乘以 2,这可以在绘制散点图时控制点的大小,人口越多,点越大。此外,我们还可以注释人口密度高的点,我们可以使用该plt.annotate()方法来完成。

df_new = pd.DataFrame(imputted_data, columns=["Expectancy", "GDP", "Population"])
df_new["Country"] = GDP_data.Country.tolist()
df_new = df_new[["Country", "Expectancy", "GDP", "Population"]]
for col in df_new.columns: 
    if col != "Country": 
        df_new[col] = df_new[col].apply(lambda x: round(x, 3))
df_country = df_new.groupby("Country").mean().reset_index()
df_country = df_country[["Country", "Expectancy", "GDP", "Population"]]
country = df_country["Country"]
GDP = df_country["GDP"]
life_exp = df_country["Expectancy"]
factor = 1000000
population = (df_country["Population"]/factor)*2
plt.figure(figsize=(15, 8)) 
plt.scatter(GDP, life_exp, s = population, alpha=0.9)
df_high_pop = df_country[df_country["Population"] >= 100000000]
for row in df_high_pop.to_dict(orient="records"): 
    plt.annotate(row["Country"], (row["GDP"], row["Expectancy"]+0.3), fontsize=10)
plt.xscale('log') 
plt.xlabel('人均国内生产总值(美元)(对数尺度)') 
plt.ylabel('预期寿命[以年计]') 
plt.title('全球GDP与预期寿命(2018)',fontweight="bold")
plt.show() 

输出结果:

接下来还可以继续优化我们的散点图。比如在我们的数据中对每个国家/地区的人口密度点进行颜色编码,然后根据人数分配不同的颜色;

此外,我们还可以使用plt.legend()增加图例,如下图所示。

回归

进一步优化:基于KNN算法的新方法使得我们现在可以更便捷地处理缺失值,并且与直接用均值、中位数相比更为可靠。利用“近朱者赤”的KNN算法原理,这种插补方法借助其他特征的分布来对目标特征进行缺失值填充。

# sklearn 
from sklearn.impute import KNNImputer 
from sklearn.linear_model import ElasticNetCV

imputer = KNNImputer(n_neighbors=3) 
imputted_data = imputer.fit_transform(df[["Expectancy", "GDP", "Population"]]) 

我们另外还想在散点图上画一条非常漂亮的线,用于帮助我们提供一种快速评估各个国家相对于总体趋势的状况的方法。我们可以使用Scikit-learn中的ElasticNet,它是一个使用 L1 和 L2 正则化训练的线性回归模型。它是 LASSO 和岭回归技术的混合体,因此它也非常适合显示严重多重共线性(特征彼此高度相关)的模型。

部分代码(完整下载见文末):

if regression: 
    reg = ElasticNetCV(cv=5, random_state=0)
    X, y = np.array(GDP).reshape(-1, 1), life_exp
    reg.fit(X,y) 
    y_pred = reg.predict(X) 
    reg_data = pd.DataFrame(X, columns=["X"]) 
    reg_data["y_pred"] = y_pred 
    reg_data = reg_data.sort_values(by="X").reset_index().drop("index", axis=1)
    reg_data = reg_data[reg_data["y_pred"] <= 90]

使用训练好的模型,绘制一条拟合曲线:

人生苦短,快学Python!

如果喜欢今天分享的文章,别忘了给我们点赞支持一下!

大家如果本文涉及的代码感兴趣,可以点击下方卡片,关注公众号【朱小五】(非本号)后台回复“花卉”即可获取对应【图片+完整代码】文件。


最近我花了两年写的新书已经上市,也算是我在CSDN博客分享Python知识3年的一个总结!

《快学Python:自动化办公轻松实战》点击蓝字查看书籍详情,感谢支持

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

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

相关文章

【Servlet篇】如何解决Request请求中文乱码的问题?

前言 前面一篇文章我们探讨了 Servlet 中的 Request 对象&#xff0c;Request 请求对象中封装了请求数据&#xff0c;使用相应的 API 就可以获取请求参数。 【Servlet篇】一文带你读懂 Request 对象 也许有小伙伴已经发现了前面的方式获取请求参数时&#xff0c;会出现中文乱…

【Spark分布式内存计算框架——Spark Streaming】4.入门案例(下)Streaming 工作原理

2.3 Streaming 工作原理 SparkStreaming处理流式数据时&#xff0c;按照时间间隔划分数据为微批次&#xff08;Micro-Batch&#xff09;&#xff0c;每批次数据当做RDD&#xff0c;再进行处理分析。 以上述词频统计WordCount程序为例&#xff0c;讲解Streaming工作原理。 创…

[数据结构]:06-队列(链表)(C语言实现)

目录 前言 已完成内容 队列实现 01-开发环境 02-文件布局 03-代码 01-主函数 02-头文件 03-QueueCommon.cpp 04-QueueFunction.cpp 结语 前言 此专栏包含408考研数据结构全部内容&#xff0c;除其中使用到C引用外&#xff0c;全为C语言代码。使用C引用主要是为了简化…

Spring Cache的使用--快速上手篇

系列文章目录 分页查询–Java项目实战篇 全局异常处理–Java实战项目篇 完善登录功能–过滤器的使用 更多该系列文章请查看我的主页哦 文章目录系列文章目录前言一、Spring Cache介绍二、Spring Cache的使用1. 导入依赖2. 配置信息3. 在启动类上添加注解4. 添加注解4.1 CacheP…

duboo+zookeeper分布式架构入门

分布式 dubbo Zookeeper 分布式系统就是若干独立计算机的集合&#xff08;并且这些计算机之间相互有关联&#xff0c;就像是一台计算机中的C盘F盘等&#xff09;&#xff0c;这些计算对于用户来说就是一个独立的系统。 zookeeper安装 下载地址&#xff1a;Index of /dist/z…

MyBatis——增删改查操作的实现

开启mybatis sql日志打印 可以在日志中看到sql中执行的语句 在配置文件中加上下面这几条语句 mybatis.configuration.log-implorg.apache.ibatis.logging.stdout.StdOutImpl logging.level.com.example.demodebug查询操作 根据用户id查询用户 UserMapper&#xff1a; User…

RTD2169芯片停产|完美替代RTD2169芯片|CS5260低BOM成本替代RTD2169方案设计

RTD2169芯片停产|完美替代RTD2169芯片|CS5260低BOM成本替代RTD2169方案设计 瑞昱的RTD2169芯片目前已经停产了&#xff0c; 那么之前用RTD2169来设计TYPEC转VGA方案的产品&#xff0c;该如何生产这类产品&#xff1f;且RTD2169芯片价格较贵&#xff0c;芯片封装尺寸是QFN40&…

JS函数的4种调用方式

函数可以声明定义&#xff0c;也可以是一个表达式&#xff0c;函数使用关键字function定义函数被定义时&#xff0c;函数内部的代码不会执行函数被调用时&#xff0c;函数内部的代码才会执行函数有四种调用方式&#xff0c;每种方式的不同在于this的初始化。&#xff08;this是…

HTML#1快速入门

一. 简介HTML是一门语言, 所有的网页都是用HTML编写的HTML(Hyper Text Markup Language): 超文本(超越了文本限制,除了文字信息还可以定义图片,音频,视频等)标记语言(有标签构成的语言)W3C标准: 网页主要由三部分组成(1) 结构: HTML(2) 表现: CSS(3) 行为: JavaScript二. 快速入…

optional说明

1.说明 public final class Optional<T> extends Object 可能包含或不包含非空值的容器对象。 如果一个值存在&#xff0c; isPresent()将返回true和get()将返回值。 提供依赖于存在或不存在包含值的其他方法&#xff0c;例如orElse() &#xff08;如果值不存在则返回…

印度这事真的干的挺棒的! |

来源&#xff1a;statista最近逛外网看到一张图&#xff0c;是关于印度家庭自来水供应的对比图。Crore是印度的单位千万(卢比)&#xff0c;所以他们从2019年供应3.23千万家庭&#xff0c;增长到了2022年的9.57万家庭&#xff0c;印度这事真的干的挺棒的&#xff01;一直以来印度…

【USB】windows热插拔通知接口分析

文章目录接口介绍概述过滤器介绍举例接收通知创建窗口参考文档接口介绍 概述 window提供了RegisterDeviceNotificationW方法&#xff0c;可以用来监听设备的热插拔事件。 HDEVNOTIFY RegisterDeviceNotificationW([in] HANDLE hRecipient,[in] LPVOID NotificationFilter,[in]…

Android 多种支付方式的优雅实现

场景App 的支付流程&#xff0c;添加多种支付方式&#xff0c;不同的支付方式&#xff0c;对应的操作不一样&#xff0c;有的会跳转到一个新的webview&#xff0c;有的会调用系统浏览器&#xff0c;有的会进去一个新的表单页面&#xff0c;等等。并且可以添加的支付方式也是不确…

计算机网络-网络核心(day02)

网络核心 最主要的功能&#xff1a; 数据交换的功能 转发&#xff0c;路由 主要分为线路交换&#xff0c;分组交换 线路交换 可以认为所有的电话通信都是线路交换 线路交换&#xff0c;比如打电话&#xff0c;需要先建立连接&#xff08;主机要经过哪些链路哪些交换机&#…

软件测试之因果图法

因果图法 1. 概述 因果图法是一种**利用图解法分析输入条件、输出结果的各种组合情况,**从而设计测试用例的方法. 因果图法适用于有多个输入和多个输出&#xff0c;而且输入和输入之间有相互的组合关系&#xff0c;输入和输出之间有相互的制约和依赖关系. 使用场景和判定表…

第一个 Spring MVC 注解式开发案例(初学必看)

✅作者简介&#xff1a;2022年博客新星 第八。热爱国学的Java后端开发者&#xff0c;修心和技术同步精进。 &#x1f34e;个人主页&#xff1a;Java Fans的博客 &#x1f34a;个人信条&#xff1a;不迁怒&#xff0c;不贰过。小知识&#xff0c;大智慧。 &#x1f49e;当前专栏…

HashMap存入一个键值对的中间发生了什么(浅读源码)

存入键值对就是调用HashMap.put()过程&#xff08;面试高频问题&#xff09;首先放出粗狂的总结假如是Integer类型就会先查看IntegerCache中是否存在这个数字&#xff0c;有就从缓存中调用&#xff0c;没有则创建新的Integer对象&#xff08;String类型没有这个过程&#xff0c…

【JavaSE】复习(进阶)

文章目录1.final关键字2.常量3.抽象类3.1概括3.2 抽象方法4. 接口4.1 接口在开发中的作用4.2类型和类型之间的关系4.3抽象类和接口的区别5.包机制和import5.1 包机制5.2 import6.访问控制权限7.Object7.1 toString()7.2 equals()7.3 String类重写了toString和equals8.内部类8.1…

【谷粒学院】vue、axios、element-ui、node.js(44~58)

44.前端技术-vue入门 &#x1f9e8;Vue.js 是什么 Vue (读音 /vjuː/&#xff0c;类似于 view) 是一套用于构建用户界面的渐进式框架。 Vue 的核心库只关注视图层&#xff0c;不仅易于上手&#xff0c;还便于与第三方库或既有项目整合。另一方面&#xff0c;当与现代化的工具…

RK3568编译Android11和目录讲解

文章目录 前言一、下载android11源码二、环境搭建1.增加交换内存三、编译瑞芯微原厂源码四、目录讲解总结前言 本文记录在Ubuntu18.04中编译Android11,只有编译了源码,后面才能进行驱动的开发,有兴趣的小伙伴可以和我一起学习吧! 提示:以下是本篇文章正文内容,下面案例可…