# ========== 数据预处理 ==========
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from mpl_toolkits.mplot3d import Axes3D
from matplotlib.animation import FuncAnimation
def preprocess_data(file_path):
"""
数据预处理函数
:param file_path: 数据文件路径
:return: 处理后的DataFrame
"""
# 读取数据
df = pd.read_csv(file_path)
# 数据清洗
df = df.dropna(subset=['latitude', 'longitude', 'acq_date'])
df['acq_date'] = pd.to_datetime(df['acq_date'])
# 时间范围筛选(2019年9月-2020年2月)
mask = (df['acq_date'] >= '2019-09-01') & (df['acq_date'] <= '2020-02-28')
df = df.loc[mask]
# 特征工程
df['year'] = df['acq_date'].dt.year
df['month'] = df['acq_date'].dt.month
df['day'] = df['acq_date'].dt.day
# 异常值处理
df = df[(df['confidence'] >= 30) & (df['confidence'] <= 100)]
return df
# ========== 主程序 ==========
if __name__ == "__main__":
# 数据预处理
cleaned_df = preprocess_data('fire_archive_M6_96619.csv')
# 设置可视化风格
plt.style.use('ggplot')
sns.set_palette("husl")
# ========== 可视化部分 ==========
# 1. 散点图(地理分布)
plt.figure(figsize=(14, 8))
scatter = plt.scatter(
cleaned_df['longitude'],
cleaned_df['latitude'],
c=cleaned_df['confidence'],
cmap='YlOrRd',
alpha=0.6,
edgecolors='w',
s=40
)
plt.colorbar(scatter, label='置信度')
plt.title('2019-2020澳大利亚丛林大火地理分布', fontsize=14)
plt.xlabel('经度', fontsize=12)
plt.ylabel('纬度', fontsize=12)
plt.tight_layout()
plt.savefig('scatter_plot.png', dpi=300)
plt.close()
# 2. Hexbin热力图(替代Folium)
plt.figure(figsize=(14, 8))
hb = plt.hexbin(
cleaned_df['longitude'],
cleaned_df['latitude'],
gridsize=100,
cmap='YlOrRd',
mincnt=1,
alpha=0.9
)
plt.colorbar(hb, label='火灾密度')
plt.title('火灾点密度分布', fontsize=14)
plt.xlabel('经度', fontsize=12)
plt.ylabel('纬度', fontsize=12)
plt.tight_layout()
plt.savefig('hexbin_heatmap.png', dpi=300)
plt.close()
# 3. 时间序列图
plt.figure(figsize=(14, 6))
daily_counts = cleaned_df.resample('D', on='acq_date').size()
daily_counts.plot(
kind='line',
color='#e34a33',
linewidth=1.5,
marker='o',
markersize=4
)
plt.title('每日火灾发生趋势', fontsize=14)
plt.xlabel('日期', fontsize=12)
plt.ylabel('火灾次数', fontsize=12)
plt.grid(True, alpha=0.3)
plt.tight_layout()
plt.savefig('time_series.png', dpi=300)
plt.close()
# 4. 月度分布柱状图
month_labels = ['2019-09', '2019-10', '2019-11',
'2019-12', '2020-01', '2020-02']
plt.figure(figsize=(12, 6))
sns.barplot(
x='month',
y='confidence',
data=cleaned_df,
estimator=np.size,
ci=None,
palette='OrRd_r'
)
plt.xticks(ticks=range(6), labels=month_labels)
plt.title('月度火灾数量分布', fontsize=14)
plt.xlabel('月份', fontsize=12)
plt.ylabel('火灾次数', fontsize=12)
plt.tight_layout()
plt.savefig('monthly_dist.png', dpi=300)
plt.close()
# 5. 置信度分布箱线图
plt.figure(figsize=(12, 6))
sns.boxplot(
x='month',
y='confidence',
data=cleaned_df,
palette='YlOrBr',
showfliers=False
)
plt.xticks(ticks=range(6), labels=month_labels)
plt.title('置信度月度分布箱线图', fontsize=14)
plt.xlabel('月份', fontsize=12)
plt.ylabel('置信度', fontsize=12)
plt.tight_layout()
plt.savefig('confidence_boxplot.png', dpi=300)
plt.close()
# 6. 3D地形图
fig = plt.figure(figsize=(16, 10))
ax = fig.add_subplot(111, projection='3d')
scatter_3d = ax.scatter(
cleaned_df['longitude'],
cleaned_df['latitude'],
cleaned_df['confidence'],
c=cleaned_df['frp'],
cmap='hot',
s=20,
alpha=0.7
)
ax.set_xlabel('经度', fontsize=12)
ax.set_ylabel('纬度', fontsize=12)
ax.set_zlabel('置信度', fontsize=12)
plt.title('3D火灾特征分布图', fontsize=14)
fig.colorbar(scatter_3d, label='辐射功率 (FRP)')
plt.tight_layout()
plt.savefig('3d_plot.png', dpi=300)
plt.close()
# 7. 昼夜分布环形图
daynight = cleaned_df['daynight'].value_counts()
plt.figure(figsize=(10, 10))
plt.pie(
daynight,
labels=['日间', '夜间'],
colors=['#ff9999', '#66b3ff'],
autopct='%1.1f%%',
startangle=90,
wedgeprops=dict(width=0.4, edgecolor='w')
)
plt.title('昼夜火灾分布比例', fontsize=14)
plt.tight_layout()
plt.savefig('daynight_pie.png', dpi=300)
plt.close()
# 8. 动态传播图(生成动画)
dates = sorted(cleaned_df['acq_date'].unique())
fig, ax = plt.subplots(figsize=(14, 8))
def animate(i):
ax.clear()
daily_data = cleaned_df[cleaned_df['acq_date'] == dates[i]]
ax.scatter(
daily_data['longitude'],
daily_data['latitude'],
c=daily_data['frp'],
cmap='Reds',
s=50,
alpha=0.7
)
ax.set_title(f'火灾传播动态 ({dates[i].strftime("%Y-%m-%d")})', fontsize=14)
ax.set_xlabel('经度', fontsize=12)
ax.set_ylabel('纬度', fontsize=12)
ani = FuncAnimation(
fig,
animate,
frames=len(dates),
interval=300,
repeat_delay=2000
)
ani.save('fire_evolution.gif', writer='pillow', fps=3)
plt.close()
print("所有可视化图表已生成完成")详细解释数据如何进行的处理和每一个可视化图的含义
最新发布