鱼C论坛

 找回密码
 立即注册
查看: 1315|回复: 3

[已解决]新手python代码修改指导

[复制链接]
发表于 2023-4-17 19:00:36 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
import os

import geopandas as gpd
import matplotlib.patches as mpatches
import matplotlib.path as mpath
import matplotlib.pyplot as plt
import numpy as np
import pandas as pd
from scipy.interpolate import Rbf

plt.rcParams['font.sans-serif'] = ['SimHei']

csv_folder = "savexg"
df_list = []
for filename in os.listdir(csv_folder):
    if filename.endswith(".csv"):
        filepath = os.path.join(csv_folder, filename)
        df = pd.read_csv(filepath)
        df_list.append(df)

# 合并所有DataFrame
df = pd.concat(df_list, ignore_index=True)
df["lat"] = df["lat"].apply(lambda x: x / 100.0 if x > 1800 else x / 10)
df["lon"] = df["lon"].apply(lambda x: x / 100.0 if x > 1800 else x / 10)
df




columns = ['R95P', 'RD95', 'RI95', 'RC95', 'R99p', 'PPER']
columns_name = ['极端降水量', '极端降水频数', '极端降水强度', '极端降水贡献率', '极端强降水量', '降水率']
columns_name = dict(zip(columns, columns_name))




def smooth(scalars, weight):
    last = scalars[0]
    smoothed = list()

    for point in scalars:
        smoothed_val = last * weight + (1 - weight) * point
        smoothed.append(smoothed_val)  # Save it
        last = smoothed_val

    return smoothed


def plot_year_data(x, y, c):
   
    plt.plot(x, y)

    # 给y设置从0开始的索引
    y = y.reset_index(drop=True)

    # 绘制趋势线
    plt.plot(x, smooth(y, 0.9), color='red')

    # 设置图表标题和轴标签
    plt.title(f"平均{columns_name[c]}")
    plt.xlabel("年份")
    plt.ylabel(columns_name[c])

    # 显示图表
    plt.savefig(f"plots/year-{c}.jpg", dpi=300)
    plt.show()


for col in columns:
    if col == 'PPER':
        continue
    yearly_data = df.groupby("year")[col].mean()
    plot_year_data(yearly_data.index, yearly_data, col)








# 将年份、月份、日期合并为一个date列
df['date'] = pd.to_datetime(df[['year', 'month', 'day']])

# 按年份分组,并计算每年的总天数和PRE不为0的天数
grouped = df.groupby(df['date'].dt.year)['PRE'].agg(['count', lambda x: (x != 0).sum()])
grouped.columns = ['total_days', 'nonzero_days']

print(grouped)

# 计算PRE不为0的天数占比
grouped['precipitation_rate'] = grouped['nonzero_days'] / grouped['total_days']

plot_year_data(grouped.index, grouped['precipitation_rate'], 'PPER')





def plot_lat_lng_data(lat_data, lon_data, value, c):
    huaih_border = gpd.read_file('HuaiH_Border.shp')

    # 设置绘图范围为shu文件的范围
    ax = huaih_border.plot(color='black', edgecolor='black')

    # print(location_data[location_data[col] == location_data[col].max()])
    # 将数据转换为网格格式
    lon = np.linspace(lon_data.min() - 1, lon_data.max(), 100)
    lat = np.linspace(lat_data.min() - 1, lat_data.max(), 100)

    lon, lat = np.meshgrid(lon, lat)

    rbf_data = Rbf(lon_data, lat_data, value, function='linear')(
        lon, lat)

    # print(rbf_data.max())

    # 绘制等高线图
    # 如果c为RD95,则设置等高线图的颜色范围为18.5-22,保留一位小数

    if c == 'RD95':
        contour= ax.contourf(lat, lon, rbf_data, cmap='rainbow', levels=np.arange(18.5, 20.5, 0.1))
    else:
        contour = ax.contourf(lat, lon, rbf_data, cmap='rainbow', levels=20)

    plt.colorbar(contour)

    # 创建剪切路径对象
    border_path = mpath.Path(huaih_border.geometry.iloc[0].coords)
    patch = mpatches.PathPatch(border_path, transform=ax.transData, facecolor='none', edgecolor='black')

    for i, contour in enumerate(contour.collections):
        contour.set_clip_path(patch)

    plt.xlabel('经度')
    plt.ylabel('纬度')
    plt.title(f'{columns_name[c]}等高线图')

    # 限制等高线图范围在shp文件轮廓内
    ax.set_xlim(huaih_border.total_bounds[0] - 0.5, huaih_border.total_bounds[2] + 0.5)
    ax.set_ylim(huaih_border.total_bounds[1] - 0.5, huaih_border.total_bounds[3] + 0.5)

    plt.savefig(f"plots/contour-{col}.jpg", dpi=300)
    plt.show()


for col in columns:
    if col == 'PPER':
        continue
    location_data = df.groupby(["lat", "lon"])[col].mean().reset_index()
    plot_lat_lng_data(location_data["lat"], location_data["lon"], location_data[col], col)




大佬们我想问一下,运行这个程序画出的图片存在了哪里?还有就是绘制趋势线那部分画出的趋势线并不平滑,我要怎么更改?
最佳答案
2023-4-17 19:03:07
您好!关于您的问题,我在这里回答:

1、运行程序后生成的图片保存在哪里?
在代码中,您使用了plt.savefig()函数将生成的图片保存到文件。图片文件将保存在名为plots的文件夹下,如果您的当前工作目录中没有这个文件夹,请先创建一个。例如,以下代码将生成一个名为year-R95P.jpg的图片并保存在plots文件夹下:
plt.savefig(f"plots/year-{c}.jpg", dpi=300)

2、关于趋势线平滑问题
您使用了smooth()函数来平滑趋势线。当前smooth()函数中的权重值weight设为0.9,如果趋势线不够平滑,您可以尝试调整该权重值。权重值越接近1,趋势线就越平滑;权重值越接近0,趋势线就越接近原始数据。您可以根据需要进行调整。

例如,您可以将权重值调整为0.95,然后观察趋势线的平滑程度是否满足您的需求:
plt.plot(x, smooth(y, 0.95), color='red')

调整权重值后,重新运行程序并查看生成的趋势线图。如果仍然不满足要求,您可以尝试调整权重值直至达到满意的效果。

祝您编程愉快!
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2023-4-17 19:01:41 | 显示全部楼层
本帖最后由 sfqxx 于 2023-4-17 19:02 编辑

关于第一个问题,程序运行画出的图片存储在名为"plots"的文件夹中,可以在程序中找到对应的代码行,查看保存的文件名和格式。

关于第二个问题,可以调整函数smooth中权重参数weight的值来改变趋势线的平滑程度。一般情况下,可以将weight值设为0.9或更高来获得比较平滑的趋势线。如果需要更加平滑的趋势线,可以适当增加该值。如果需要更少平滑的趋势线,可以适当降低该值。
有用请设置最佳答案
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-4-17 19:03:07 | 显示全部楼层    本楼为最佳答案   
您好!关于您的问题,我在这里回答:

1、运行程序后生成的图片保存在哪里?
在代码中,您使用了plt.savefig()函数将生成的图片保存到文件。图片文件将保存在名为plots的文件夹下,如果您的当前工作目录中没有这个文件夹,请先创建一个。例如,以下代码将生成一个名为year-R95P.jpg的图片并保存在plots文件夹下:
plt.savefig(f"plots/year-{c}.jpg", dpi=300)

2、关于趋势线平滑问题
您使用了smooth()函数来平滑趋势线。当前smooth()函数中的权重值weight设为0.9,如果趋势线不够平滑,您可以尝试调整该权重值。权重值越接近1,趋势线就越平滑;权重值越接近0,趋势线就越接近原始数据。您可以根据需要进行调整。

例如,您可以将权重值调整为0.95,然后观察趋势线的平滑程度是否满足您的需求:
plt.plot(x, smooth(y, 0.95), color='red')

调整权重值后,重新运行程序并查看生成的趋势线图。如果仍然不满足要求,您可以尝试调整权重值直至达到满意的效果。

祝您编程愉快!
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-4-17 19:04:06 | 显示全部楼层
根据程序中的代码,图片会保存在当前目录下的plots文件夹中,分别命名为"year-c.jpg"和"contour-c.jpg",其中c代表某一列(变量)的名称。

要更改绘制趋势线的平滑程度,可以调整smooth()函数内的weight参数。将参数设置得更接近1会使曲线更平滑,而将参数设置得更接近0会使曲线更不平滑或者更加抖动。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-9-23 17:15

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表