Python绘制数据(二)

一、模拟掷一个骰子

1、什么是Plotly

Plotly 是一个强大的数据可视化工具,主要能干以下几件事:

  • 创建多种图表:支持丰富的图表类型,包括折线图、柱状图、散点图等基础图表,也能绘制等高线图、热力图、箱线图等复杂图表,还可制作地图、散点地图等地理可视化图表以及 3D 图表,满足不同数据展示需求。
  • 实现交互操作:生成的图表具有高度交互性,用户可通过鼠标悬停查看数值和标签,能进行缩放、平移操作来查看细节,还可点击图例动态显示或隐藏数据系列,三维图表还能进行旋转,方便深入探索数据。
  • 高度自定义样式:允许用户对图表的标题、坐标轴标签、刻度、网格线等基本元素,以及数据点的标记样式、线条样式、填充颜色等进行自定义,对于地图和 3D 图表,还能设置投影方式、视角、光照效果等,打造个性化图表。
  • 集成与分享:可与 Jupyter Notebook 集成,便于在数据分析过程中直接可视化。借助 Dash 框架能创建 Web 应用,用于构建数据可视化仪表盘。生成的图表可导出为 HTML 文件,也能保存为高清 PNG、SVG 等图片格式,方便分享和嵌入到其他文档或网页中。
  • 实时数据可视化:通过更新数据源,能够实现实时更新图表,适用于实时监控等场景,如实时股票价格监控、服务器性能监控等。

2、安装Plotly

file->settings->Project:xxx->Python Interpreter->点击+->输入Plotly安装即可。

3、编写骰子类

python 复制代码
from random import randint

class Die:
    """表示一个骰子的类"""
    
    def __init__(self, sides = 6):
        """初始化骰子的属性
        sides: 骰子的面数,默认为6面
        """
        self.sides = sides  # 存储骰子的面数

    def roll(self):
        """模拟掷骰子,返回一个1到sides之间的随机整数"""
        return randint(1, self.sides)  # 使用randint生成随机数

4、编写掷骰子的类

python 复制代码
from plotly.graph_objs import Layout, Bar
from plotly import offline
from Die import Die  # 导入自定义的骰子类

# 创建一个六面骰子实例
die = Die()

# 掷骰子100次并存储结果
results = []
for roll_num in range(100):
    results.append(die.roll())  # 调用Die类的roll方法获取随机结果
print(results)  # 打印所有掷骰子的结果

# 分析结果:统计每个点数出现的频率
frequencies = []
for value in range(1, die.sides + 1):  # 遍历1到骰子面数的所有可能值
    frequency = results.count(value)  # 统计每个值在结果中出现的次数
    frequencies.append(frequency)  # 将频率添加到列表
print(frequencies)  # 打印频率统计结果

# 数据可视化:使用Plotly创建柱状图
x_values = list(range(1, die.sides + 1))  # x轴为骰子的各个面
data = [Bar(x=x_values, y=frequencies)]  # 创建柱状图数据对象

# 配置坐标轴
x_axis_config = {'title': '骰子点数'}  # x轴标题
y_axis_config = {'title': '出现频率'}  # y轴标题

# 设置图表布局
my_layout = Layout(
    title='投掷一个D6骰子100次的结果分布',  # 图表标题
    xaxis=x_axis_config,  # 应用x轴配置
    yaxis=y_axis_config   # 应用y轴配置
)

# 生成HTML文件并打开浏览器显示图表
# 注意:此处路径中的转义字符需要使用双反斜杠或原始字符串
offline.plot(
    {'data': data, 'layout': my_layout},
    filename=r'D:\py_projects\test1\die_visual.html'  # 保存为HTML文件
)

代码解释:

1. 导入必要的库和模块

python 复制代码
from plotly.graph_objs import Layout, Bar
from plotly import offline
from Die import Die  # 导入自定义的骰子类
  • LayoutBar 是 Plotly 中用于创建图表布局和柱状图的类。
  • offline 模块允许在本地生成 HTML 文件来显示图表,无需连接网络。
  • Die 是一个自定义类,用于模拟骰子。

2. 创建骰子实例并掷骰子

python 复制代码
# 创建一个六面骰子实例
die = Die()

# 掷骰子100次并存储结果
results = []
for roll_num in range(100):
    results.append(die.roll())  # 调用Die类的roll方法获取随机结果
print(results)  # 打印所有掷骰子的结果
  • die = Die() 创建一个默认的六面骰子。
  • 通过循环 100 次调用 die.roll() 方法模拟掷骰子,并将每次结果存储在 results 列表中。
  • 最后打印出所有 100 次掷骰子的结果。

3. 分析结果:统计每个点数出现的频率

python 复制代码
# 分析结果:统计每个点数出现的频率
frequencies = []
for value in range(1, die.sides + 1):  # 遍历1到骰子面数的所有可能值
    frequency = results.count(value)  # 统计每个值在结果中出现的次数
    frequencies.append(frequency)  # 将频率添加到列表
print(frequencies)  # 打印频率统计结果
  • frequencies 列表用于存储每个点数出现的次数。
  • range(1, die.sides + 1) 生成从 1 到 6 的整数(假设是六面骰子)。
  • results.count(value) 统计每个点数在 results 列表中出现的次数,并将结果添加到 frequencies 列表。
  • 最后打印出每个点数的出现频率。

4. 数据可视化:创建柱状图

python 复制代码
# 数据可视化:使用Plotly创建柱状图
x_values = list(range(1, die.sides + 1))  # x轴为骰子的各个面
data = [Bar(x=x_values, y=frequencies)]  # 创建柱状图数据对象
  • x_values 是一个包含 1 到 6 的列表,表示骰子的六个面。
  • Bar 对象创建一个柱状图,其中 x 轴为骰子的各个面,y 轴为对应的出现频率。
  • data 列表包含这个 Bar 对象,用于后续的图表创建。

5. 配置图表布局

python 复制代码
# 配置坐标轴
x_axis_config = {'title': '骰子点数'}  # x轴标题
y_axis_config = {'title': '出现频率'}  # y轴标题

# 设置图表布局
my_layout = Layout(
    title='投掷一个D6骰子100次的结果分布',  # 图表标题
    xaxis=x_axis_config,  # 应用x轴配置
    yaxis=y_axis_config   # 应用y轴配置
)
  • x_axis_configy_axis_config 分别设置 x 轴和 y 轴的标题。
  • Layout 对象定义了整个图表的布局,包括标题和坐标轴配置。

6. 生成 HTML 文件并显示图表

python 复制代码
# 生成HTML文件并打开浏览器显示图表
# 注意:此处路径中的转义字符需要使用双反斜杠或原始字符串
offline.plot(
    {'data': data, 'layout': my_layout},
    filename='D:\\py_projects\\test1\\die_visual.html'  # 保存为HTML文件
)
  • offline.plot() 方法将数据和布局组合成一个完整的图表,并生成一个 HTML 文件。
  • filename 参数指定了 HTML 文件的保存路径,使用原始字符串(前面加 r)避免反斜杠转义问题。
  • 运行代码后,会自动在浏览器中打开生成的 HTML 文件,显示柱状图。

二、模拟掷两个骰子

python 复制代码
from plotly.graph_objs import Layout, Bar
from plotly import offline
from Die import Die

# 创建两个六面骰子实例(D6)
die1 = Die()
die2 = Die()

# 掷骰子多次并将每次结果存储到列表中
results = []
for roll_num in range(1000):  # 增加投掷次数以获得更平滑的分布
    result = die1.roll() + die2.roll()  # 计算两个骰子的点数之和
    results.append(result)

# 分析结果:统计每个可能的点数之和出现的频率
frequencies = []
max_value = die1.sides + die2.sides  # 最大可能值为两个骰子面数之和(6+6=12)

# 注意:两个骰子的最小和为2(1+1),因此从2开始循环
for value in range(2, max_value + 1):
    frequency = results.count(value)  # 统计每个和值出现的次数
    frequencies.append(frequency)

# 数据可视化:使用Plotly创建柱状图
x_values = list(range(2, max_value + 1))  # x轴为所有可能的和值(2到12)
data = [Bar(x=x_values, y=frequencies)]  # 创建柱状图数据

# 配置图表布局和坐标轴
x_axis_config = {
    'title': '两个骰子的点数之和',  # x轴标题
    'dtick': 1  # 设置x轴刻度间隔为1,确保每个和值都显示
}

y_axis_config = {
    'title': '出现频率'  # y轴标题
}

my_layout = Layout(
    title='掷两个六面骰子1000次的结果分布',  # 图表标题
    xaxis=x_axis_config,  # 应用x轴配置
    yaxis=y_axis_config   # 应用y轴配置
)

# 生成HTML文件并在浏览器中显示图表
offline.plot(
    {'data': data, 'layout': my_layout},
    filename=r'D:\py_projects\test1\two_dice_visualization.html'  # 保存路径
)

三、读取csv文件数据绘制数据图

1、打印头文件及其位置

python 复制代码
import csv

# 指定CSV文件路径
fileName = 'D:\\py_projects\\data\\sitka_weather_07-2018_simple.csv'

# 打开CSV文件
with open(fileName) as csvfile:
    # 创建CSV阅读器对象
    reader = csv.reader(csvfile)

    head_row = next(reader)

    for index,row in enumerate(head_row):
        print(index,row)

代码解释:

1. 导入 CSV 模块

python 复制代码
import csv
  • 作用:导入 Python 内置的csv模块,用于处理 CSV(逗号分隔值)格式文件
  • CSV 模块提供了读取和写入 CSV 文件的功能

2. 指定 CSV 文件路径

python 复制代码
fileName = 'D:\\py_projects\\data\\sitka_weather_07-2018_simple.csv'
  • 作用:定义要读取的 CSV 文件的路径
  • 路径使用双反斜杠\\是为了转义特殊字符,确保路径正确解析
  • 示例文件是一个天气数据文件(可能包含日期、温度等信息)

3. 打开并读取 CSV 文件

python 复制代码
with open(fileName) as csvfile:
    reader = csv.reader(csvfile)
  • with open(fileName) as csvfile:使用with语句打开文件,自动管理文件资源(无需手动关闭)
  • csv.reader(csvfile):创建一个 CSV 阅读器对象,用于逐行读取文件内容
  • 默认情况下,csv.reader会将每行数据按逗号分隔并转换为列表

4. 获取表头行

python 复制代码
head_row = next(reader)
  • next(reader):获取迭代器的下一行数据(即第一行)
  • 通常 CSV 文件的第一行是表头,包含列名信息
  • 执行这一步后,阅读器的指针会移到第二行,后续读取将从第二行开始

5. 打印表头信息

python 复制代码
for index, row in enumerate(head_row):
    print(index, row)
  • enumerate(head_row):将表头列表转换为带索引的枚举对象
  • index:列的索引(从 0 开始)
  • row:列名(表头内容)

2、读取csv数据

python 复制代码
import csv

# 指定CSV文件路径
fileName = 'D:\\py_projects\\data\\sitka_weather_07-2018_simple.csv'

# 打开CSV文件
with open(fileName) as csvfile:
    # 创建CSV阅读器对象
    reader = csv.reader(csvfile)

    # 读取并存储文件头行(列名)
    header_row = next(reader)

    # 初始化最高温度列表
    highs = []

    # 遍历文件中剩余的每一行数据
    for row in reader:
        # 提取并转换最高温度数据(假设在第6列,索引为5)
        high = int(row[5])
        # 将转换后的温度添加到列表中
        highs.append(high)

# 打印提取的最高温度列表
print(highs)

代码解释:

1. 准备一个空列表,用来装最高温度

python 复制代码
highs = []
  • highs = []:就像准备一个空篮子,后面要把每天的最高温度 "放进去"。其存储的数据类型为列表

2. 一行一行地读表格,提取最高温度

python 复制代码
for row in reader:
    print(row)
    high = int(row[5])
    highs.append(high)
  • for row in reader:让阅读器逐行读取表格的剩余内容(从第二行开始)。
  • print(row) :每读一行,就把这行内容打印出来看看(比如 ['2018-07-01', '16.7', '10.0'])。这里输出的是元组
  • row[5] :从当前行中取出第 6 个数据(比如 '16.7')。
    • 为什么是 5? 因为列表索引从 0 开始,所以第 6 个元素的索引是 5。
  • int(row[5]) :把温度从文本(比如 '16.7')变成数字(比如 16)。
  • highs.append(high) :把转换后的温度数字放进篮子(highs 列表)里。

3、绘制温服图表

python 复制代码
import csv
import matplotlib.pyplot as plt

# 指定CSV文件路径
fileName = 'D:\\py_projects\\data\\sitka_weather_07-2018_simple.csv'

# 打开CSV文件
with open(fileName) as csvfile:
    # 创建CSV阅读器对象
    reader = csv.reader(csvfile)

    head_row = next(reader)

    highs = []

    for row in reader:
        highs.append(int(row[5]))

#绘制表格
plt.style.use('ggplot')  #设置图表风格为 "ggplot"
fig, ax = plt.subplots()
ax.plot(highs)
#设置表格样式
ax.set_title('The highest temperature for each month in 2018',fontsize=11)
ax.set_xlabel('',fontsize=11)
ax.set_ylabel('temperature F',fontsize=11)
ax.tick_params(axis='both', which='major', labelsize=10)
plt.show() #显示绘制好的图表窗口。

代码解释:

1、创建图表与坐标轴

python 复制代码
fig, ax = plt.subplots()
  • plt.subplots():创建一个图表 (figure) 和一个子图 (axes) 对象。
    • fig:表示整个图表窗口。
    • ax:表示实际的绘图区域(坐标系)。

2、绘制折线图

python 复制代码
ax.plot(highs)
  • ax.plot(highs):在坐标系上绘制折线图。
    • X 轴:默认是数据点的索引(0-11,对应 1-12 月)。
    • Y 轴:highs列表中的值(最高气温)。

3、设置图表标题和坐标轴标签

python 复制代码
ax.set_title('The highest temperature for each month in 2018', fontsize=11)
ax.set_xlabel('', fontsize=11)
ax.set_ylabel('temperature F', fontsize=11)
  1. 标题设置

    • ax.set_title():设置图表标题为 "The highest temperature for each month in 2018"(2018 年每月最高气温)。
    • fontsize=11:标题文字大小为 11pt。
  2. X 轴标签

    • ax.set_xlabel(''):X 轴标签为空字符串(可能后续会补充月份信息)。
  3. Y 轴标签

    • ax.set_ylabel('temperature F'):Y 轴标签为 "temperature F"(华氏温度)。

4、设置刻度标签大小

python 复制代码
ax.tick_params(axis='both', which='major', labelsize=10)
  • ax.tick_params():设置坐标轴刻度的样式。
    • axis='both':同时设置 X 轴和 Y 轴。
    • which='major':只设置主刻度(默认每个月一个刻度)。
    • labelsize=10:刻度标签文字大小为 10pt。

4、在图表中添加时间

python 复制代码
import csv
import matplotlib.pyplot as plt
from datetime import datetime

# 指定CSV文件路径(包含2018年7月天气数据)
fileName = 'D:\\py_projects\\data\\sitka_weather_07-2018_simple.csv'

with open(fileName) as csvfile:
    reader = csv.reader(csvfile)
    head_row = next(reader)  # 获取表头行
    
    # 创建空列表存储最高温度和日期
    highs, dates = [], []
    
    # 遍历CSV文件的每一行数据
    for row in reader:
        # 获取最高温度列(索引5),转换为整数并添加到列表
        highs.append(int(row[5]))
        
        # 日期处理:
        # 1. 从第3列(row[2])获取原始日期字符串(格式:YYYY-MM-DD)
        # 2. 使用datetime.strptime()将字符串解析为datetime对象
        #    - '%Y-%m-%d' 是日期格式指令,对应年-月-日
        current_date = datetime.strptime(row[2], '%Y-%m-%d')
        dates.append(current_date)  # 将datetime对象存入列表

# 绘制温度随日期变化的折线图
plt.style.use('ggplot')  # 设置图表风格为 "ggplot"(类似R语言的风格)
fig, ax = plt.subplots()  # 创建图表和坐标轴对象

# 绘制折线图:
# - X轴:日期列表(datetime对象)
# - Y轴:最高温度列表
# - c='red':设置线条颜色为红色
ax.plot(dates, highs, c='red')

# 设置图表标题和样式
ax.set_title('The highest temperature for each month in 2018', fontsize=11)

# 自动格式化X轴日期标签:
# - 旋转日期标签避免重叠
# - 智能选择日期显示格式(如只显示月份、日等)
fig.autofmt_xdate()

ax.set_xlabel('', fontsize=11)  # X轴标签(为空,可根据需要添加)
ax.set_ylabel('temperature F', fontsize=11)  # Y轴标签(温度单位:华氏度)
ax.tick_params(axis='both', which='major', labelsize=10)  # 设置刻度标签大小

plt.show()  # 显示绘制好的图表窗口

5、绘制一整年的气温变化图表

只需要将文件变为

python 复制代码
fileName = 'D:\\py_projects\\data\\sitka_weather_2018_simple.csv'

6、添加最低温度

python 复制代码
import csv
import matplotlib.pyplot as plt
from datetime import datetime

fileName = 'D:\\py_projects\\data\\sitka_weather_2018_simple.csv'

with open(fileName) as csvfile:
    reader = csv.reader(csvfile)

    head_row = next(reader)

    lows,highs,dates = [],[] ,[]  #获取最高温度,最低温度和时间

    for row in reader:
        lows.append(float(row[6]))
        highs.append(int(row[5]))
        current_date = datetime.strptime(row[2], '%Y-%m-%d')
        dates.append(current_date)

#绘制表格
plt.style.use('ggplot')
fig, ax = plt.subplots()
ax.plot(dates,highs,c = 'red')  #绘制最高温度曲线
ax.plot(dates,lows,c = 'blue') #绘制最低温度曲线
#设置表格样式
ax.set_title('The highest temperature for each month in 2018',fontsize=11)
fig.autofmt_xdate()
ax.set_xlabel('',fontsize=11)
ax.set_ylabel('temperature F',fontsize=11)
ax.tick_params(axis='both', which='major', labelsize=10)
plt.show()

7、给图表区域着色

python 复制代码
import csv
import matplotlib.pyplot as plt
from datetime import datetime

fileName = 'D:\\py_projects\\data\\sitka_weather_2018_simple.csv'

with open(fileName) as csvfile:
    reader = csv.reader(csvfile)

    head_row = next(reader)

    lows,highs,dates = [],[] ,[]  #获取最高温度,最低温度和时间

    for row in reader:
        lows.append(float(row[6]))
        highs.append(int(row[5]))
        current_date = datetime.strptime(row[2], '%Y-%m-%d')
        dates.append(current_date)

#绘制表格
plt.style.use('ggplot')
fig, ax = plt.subplots()
# 绘制最高温度曲线
# - dates: X轴数据(日期列表)
# - highs: Y轴数据(最高温度列表)
# - c='red': 曲线颜色为红色
# - alpha=0.5: 曲线透明度为50%(使曲线半透明,便于查看重叠区域)
ax.plot(dates, highs, c='red', alpha=0.5)  

# 绘制最低温度曲线
# - dates: X轴数据(与最高温度使用相同的日期)
# - lows: Y轴数据(最低温度列表)
# - c='blue': 曲线颜色为蓝色
# - alpha=0.5: 曲线透明度为50%
ax.plot(dates, lows, c='blue', alpha=0.5)  

# 填充最高温度和最低温度之间的区域
# - dates: X轴数据(日期)
# - highs: 上边界(最高温度)
# - lows: 下边界(最低温度)
# - facecolor='blue': 填充颜色为蓝色
# - alpha=0.1: 填充区域透明度为10%(几乎透明,仅作视觉区分)
ax.fill_between(dates, highs, lows, facecolor='blue', alpha=0.1)  
#设置表格样式
ax.set_title('The highest temperature for each month in 2018',fontsize=11)
fig.autofmt_xdate()
ax.set_xlabel('',fontsize=11)
ax.set_ylabel('temperature F',fontsize=11)
ax.tick_params(axis='both', which='major', labelsize=10)
plt.show()
相关推荐
心中有国也有家2 小时前
GE图引擎深度解析——CANN的计算图优化与执行引擎
人工智能·pytorch·python·学习·numpy
卷毛的技术笔记3 小时前
告别硬编码!Spring AI Alibaba 实现 AI Agent 智能工具调用(Tool Calling)
java·人工智能·后端·python·spring·ai编程
编程大师哥3 小时前
匿名函数 lambda + 高阶函数
java·python·算法
isyangli_blog3 小时前
OpenDayLight (Carbon 版本) 启动与组件安装
开发语言·php
vb2008113 小时前
FastAPI APIRouter
开发语言·python
Benszen3 小时前
KVM虚拟化解决方案
开发语言·perl
会编程的土豆3 小时前
Go 语言反射(Reflection)详解
开发语言·后端·golang
東雪木3 小时前
多线程与并发编程 专属复习笔记
java·开发语言·笔记·java面试
adrninistrat0r4 小时前
Java调用链MCP分析工具
java·python·ai编程
杨充4 小时前
1.3 浮点型数据设计灵魂
开发语言·python·算法