机器中init.rc文件,在那个路径下

时间: 2025-08-07 21:20:09 AIGC 浏览: 31
<think>好的,我现在需要回答用户关于Android系统中init.rc文件的具体路径的问题。用户之前询问过如何通过修改init.rc来关闭SELinux,现在他转向了文件位置的问题。根据提供的引用内容,我需要整合这些信息来找到正确的路径。首先,引用[1]提到除了init.rc还有其他.rc文件如vendor.rc和device.rc,通过import指令导入到init.rc中。这说明init.rc可能位于根目录,而其他文件分布在不同的子目录中。引用[3]详细列出了init.rc文件的内容,其中提到了导入其他文件的路径,比如/system/etc/init/hw/下的文件。这可能暗示init.rc本身的位置。然后,引用[3]中的目录结构显示,在Android11中,init.rc可能位于根目录,即/init.rc,而其他相关的.rc文件在/system/etc/init/hw/和/vendor/etc/init/hw/等目录下。例如,/init.environ.rc被导入,这可能也在根目录。不过,需要确认不同Android版本的路径是否有变化。另外,引用[4]提到服务启动时检查可执行文件的存在,这可能意味着init.rc的位置需要被init进程直接访问,通常在根目录或系统分区。综合来看,标准的路径应该是根目录下的/init.rc,但不同设备可能有差异,比如厂商定制可能在/vendor/etc/init/hw/里。 需要验证不同Android版本的路径是否一致。例如,Android开源项目(AOSP)中,init.rc通常位于系统根目录,而其他设备可能根据厂商不同放在vendor分区。用户可能需要检查设备的根目录或系统分区中的特定位置。最后,用户可能需要知道如何访问这些路径,例如需要root权限,或者通过adb命令查看。同时,不同设备的路径可能不同,比如三星或华为可能有自己的结构。因此,回答中需要指出常见路径,并提醒可能的变体。</think>### Android init.rc 文件路径说明 在Android系统中,`init.rc`文件是系统初始化的核心配置文件,其标准路径为: ``` /system/core/rootdir/init.rc ``` 但实际设备中部署的路径可能因系统版本或厂商定制而有所不同,主要分为以下两种情况: #### 1. **原生AOSP路径(编译阶段)** - 源码路径: `$ANDROID_BUILD_TOP/system/core/rootdir/init.rc` 这是AOSP代码库中的原始位置,编译时会打包到系统镜像中[^3]。 #### 2. **设备运行时的实际路径** - 系统根目录: `/init.rc` 大多数Android设备会将编译后的`init.rc`直接放置在根目录下,由`init`进程在启动时加载[^1][^3]。 - 厂商定制路径(部分设备): `/vendor/etc/init/hw/init.rc` 某些厂商(如华为、三星)可能将定制化的`init.rc`放在`vendor`分区中[^1]。 #### 验证方法 可通过ADB命令检查实际路径: ```bash adb shell ls -l /init.rc # 或搜索全盘 adb shell find / -name "init.rc" 2>/dev/null ``` #### 文件结构示例 ```rc # 文件导入示例(体现路径层级) import /system/etc/init/hw/init.usb.rc import /vendor/etc/init/hw/init.rk30board.rc ``` ### 路径差异说明 | 设备类型 | 典型路径 | 修改权限要求 | |----------------|-----------------------------|--------------------| | 原生AOSP设备 | `/init.rc` | 需解Boot镜像 | | 厂商定制设备 | `/vendor/etc/init/hw/*.rc` | 需解锁vendor分区 | | 模拟器 | `/system/core/rootdir/` | 直接修改镜像文件 | ```mermaid graph TD A[init进程启动] --> B{搜索init.rc} B -->|根目录存在| C[加载/init.rc] B -->|厂商定制| D[加载/vendor/etc/init/hw/init.rc] C & D --> E[解析导入其他.rc文件] ```
阅读全文

相关推荐

1.将当前系统登录用户的信息转换为大写后保存至/tmp/who.out文件中 2. 显示当前目录并统计当前目录下文件数 3.计算1+2+3+..+99+100的总和 4.将PATH变量每个目录显示在独立的一行 5、显示/proc/meminfo文件中以大小s开头的行 6、显示/etc/passwd文件中不以/bin/bash结尾的行 7、找出/etc/passwd中的两位或三位数 8、找出“netstat -tan”命令的结果中以‘LISTEN’后跟任意多个空白字符结尾的行 9、在给定的sample.txt文件中搜索有the的行,并输出行号 10、在给定的sample.txt文件中搜索没有the的行,并输出行号 11、在给定的sample.txt文件中搜索oo前没有g的字符串所在的行. 12、在给定的sample.txt文件中搜索包含数字的行 13、在给定的sample.txt文件中搜索the在开头的行 14、在给定的sample.txt文件中搜索开头不是英文字母的行 15、在给定的sample.txt文件中搜索末尾是.的行 16、在给定的sample.txt文件中搜索空行 17、在给定的sample.txt文件中搜索两个o以上的字符串 18、在给定的sample.txt文件中搜索g开头和结尾的字符串在的行 19、在给定的sample.txt文件中搜索包含两个o的字符串的行。 20、在给定的sample.txt文件中搜索g后面跟2~5个o,后面再跟一个g的字符串的行。 21、在给定的sample.txt文件中搜索包含g后面跟2个以上o,后面再跟g的行。。 22、显示/etc/passwd 上所有系统用户的用户名和UID(注:、/etc/passwd中字段之间用 “:”分隔) 23、显示/etc/passwd三个用户root、mage、wang(注第二和第三个用户根据你机器实际情况确定)的第1、3和7个字段信息。(注:、/etc/passwd中字段之间用 “:”分隔) 24、找出/etc/rc.d/init.d/functions文件中行首为某单词(包括下划线)后面跟一个小括号的行 linux

# 导入所需的库 import pandas as pd # 导入pandas库,用于数据处理和分析,特别是DataFrame操作 import numpy as np # 导入numpy库,用于进行数值计算,特别是数组操作 import matplotlib.pyplot as plt # 导入matplotlib的pyplot模块,用于绘制图表 import matplotlib # 导入matplotlib主库,用于更底层的绘图设置 from matplotlib.patches import Patch # 从matplotlib.patches中导入Patch,用于创建图例中的色块 from sklearn.model_selection import train_test_split, GridSearchCV # 从sklearn导入数据划分和网格搜索交叉验证的工具 from sklearn.preprocessing import StandardScaler # 从sklearn导入数据标准化工具 import xgboost as xgb # 【XGBoost 修改】导入XGBoost库,用于构建梯度提升决策树模型 from sklearn.metrics import mean_absolute_error, r2_score, mean_squared_error # 从sklearn导入评估回归模型性能的指标 import joblib # 导入joblib库,用于模型的保存和加载 from scipy.stats import gaussian_kde # 从scipy.stats导入高斯核密度估计,可用于绘制密度图(此脚本中未直接使用,但可能为备用) from sklearn.inspection import PartialDependenceDisplay, partial_dependence # 从sklearn导入部分依赖图的工具(此脚本未使用,改用手动实现) import time # 导入time库,用于计时(此脚本中未直接使用) import os # 导入os库,用于操作系统相关功能,如创建文件夹 from itertools import combinations # 从itertools导入combinations,用于生成组合 import shap # 导入shap库,用于模型解释,计算SHAP值 import warnings # 导入warnings库,用于控制警告信息的显示 from collections import defaultdict # 从collections导入defaultdict,用于创建带有默认值的字典 from PyALE import ale # 导入PyALE库,用于计算和绘制累积局部效应图 from scipy.interpolate import griddata # 从scipy.interpolate导入griddata,用于插值(此脚本中未直接使用) # --- 全局设置 --- # 忽略特定类型的警告,避免在输出中显示不必要的警告信息 warnings.filterwarnings("ignore", category=FutureWarning, module="sklearn.utils._bunch") warnings.filterwarnings("ignore", category=UserWarning) matplotlib.use('TkAgg') # 设置matplotlib的后端,'TkAgg'是一个图形界面后端,确保在某些环境下可以正常显示绘图窗口 import os import tempfile # 设置临时文件夹到一个英文路径 os.environ['JOBLIB_TEMP_FOLDER'] = 'C:/temp' os.environ['TMP'] = 'C:/temp' os.environ['TEMP'] = 'C:/temp' # 确保这个目录存在 if not os.path.exists('C:/temp'): os.makedirs('C:/temp') # --- (函数定义区) --- # 定义一个函数,用于绘制回归模型的拟合效果图 def plot_regression_fit(y_true, y_pred, r2, rmse, mae, data_label_en, title_en, save_path): """ 绘制真实值与预测值的散点图,并显示模型评估指标。 y_true: 真实值 y_pred: 预测值 r2: R-squared值 rmse: 均方根误差 mae: 平均绝对误差 data_label_en: 数据集标签 (如 'Train Set') title_en: 图表标题 save_path: 图片保存路径 """ plt.style.use('seaborn-v0_8-whitegrid') # 使用预设的绘图风格 plt.rcParams['font.family'] = 'sans-serif' # 设置字体为无衬线字体,以获得更好的显示效果 fig, ax = plt.subplots(figsize=(7, 7)) # 创建一个7x7英寸的画布和子图 # 绘制真实值 vs 预测值的散点图 ax.scatter(y_true, y_pred, alpha=0.6, edgecolors='k', label=f'{data_label_en} (n={len(y_true)})') # 计算并设置坐标轴的范围,确保1:1线能完整显示 lims = [np.min([y_true.min(), y_pred.min()]) - 5, np.max([y_true.max(), y_pred.max()]) + 5] # 绘制1:1参考线 (y=x),代表完美预测 ax.plot(lims, lims, 'k--', alpha=0.75, zorder=0, label='1:1 Line (Perfect Fit)') ax.set_aspect('equal') # 设置x和y轴的比例相等 ax.set_xlim(lims) # 设置x轴范围 ax.set_ylim(lims) # 设置y轴范围 y_true_np = np.array(y_true) # 将真实值转换为numpy数组 y_pred_np = np.array(y_pred) # 将预测值转换为numpy数组 m, b = np.polyfit(y_true_np, y_pred_np, 1) # 对散点进行线性拟合,得到斜率m和截距b ax.plot(y_true_np, m * y_true_np + b, 'r-', label='Linear Fit') # 绘制线性拟合线 ax.set_xlabel('True Values (%)', fontsize=12) # 设置x轴标签 ax.set_ylabel('Predicted Values (%)', fontsize=12) # 设置y轴标签 ax.set_title(title_en, fontsize=14, weight='bold') # 设置图表标题 # 准备要在图上显示的评估指标文本 metrics_text = f'$R^2 = {r2:.3f}$\n$RMSE = {rmse:.3f}$\n$MAE = {mae:.3f}$' # 在图的左上角添加文本框,显示评估指标 ax.text(0.05, 0.95, metrics_text, transform=ax.transAxes, fontsize=12, verticalalignment='top', bbox=dict(boxstyle='round', facecolor='wheat', alpha=0.5)) ax.legend(loc='lower right') # 在右下角显示图例 fig.savefig(save_path, dpi=200, bbox_inches='tight') # 保存图表到指定路径 plt.close(fig) # 关闭图表,释放内存 # 定义一个函数,用于绘制组合特征重要性图(条形图+甜甜圈图) def plot_importance_combined(df_importance, title, save_path, bar_color='dodgerblue'): """ 绘制特征重要性条形图,并在右下角嵌入一个显示Top-N特征占比的甜甜圈图。 df_importance: 包含'Feature'和'Importance'两列的DataFrame title: 图表标题 save_path: 图片保存路径 bar_color: 条形图的颜色 """ df_importance_sorted = df_importance.sort_values(by='Importance', ascending=True) # 按重要性升序排序 plt.rc("font", family='Microsoft YaHei') # 设置中文字体为微软雅黑,以正确显示中文 fig, ax = plt.subplots(figsize=(14, 10)) # 创建一个14x10英寸的画布和子图 # 绘制水平条形图 bars = ax.barh(df_importance_sorted['Feature'], df_importance_sorted['Importance'], color=bar_color, alpha=0.8) ax.set_title(title, fontsize=18, pad=20) # 设置标题 ax.set_xlabel('重要性得分', fontsize=14) # 设置x轴标签 ax.set_ylabel('特征', fontsize=14) # 设置y轴标签 ax.tick_params(axis='both', which='major', labelsize=12) # 设置刻度标签的大小 ax.grid(axis='x', linestyle='--', alpha=0.6) # 显示x轴方向的网格线 # 在每个条形图旁边显示具体的重要性数值 for bar in bars: width = bar.get_width() ax.text(width, bar.get_y() + bar.get_height() / 2, f' {width:.4f}', va='center', ha='left', fontsize=10) ax.set_xlim(right=ax.get_xlim()[1] * 1.2) # 调整x轴范围,为数值标签留出空间 N_DONUT_FEATURES = 5 # 设置甜甜圈图中要显示的特征数量 if len(df_importance) < N_DONUT_FEATURES: # 如果总特征数小于5,则取全部特征 N_DONUT_FEATURES = len(df_importance) df_desc = df_importance.sort_values(by='Importance', ascending=False) # 按重要性降序排序 top_n_features = df_desc.head(N_DONUT_FEATURES) # 选取最重要的N个特征 donut_feature_names = top_n_features['Feature'].tolist() # 获取这N个特征的名称 # 如果有特征且总重要性大于0,则绘制甜甜圈图 if not top_n_features.empty and top_n_features['Importance'].sum() > 0: total_donut_importance = top_n_features['Importance'].sum() # 计算Top-N特征的重要性总和 donut_percentages = top_n_features['Importance'] / total_donut_importance * 100 # 计算每个特征在Top-N中的百分比 ax_inset = fig.add_axes([0.45, 0.15, 0.28, 0.28]) # 在主图上创建一个嵌入的子图(甜甜圈图的位置) colors = matplotlib.colormaps['tab10'].colors # 获取一组颜色 # 绘制饼图(通过设置width属性使其变为甜甜圈图) wedges, _ = ax_inset.pie( donut_percentages, colors=colors[:len(top_n_features)], startangle=90, counterclock=False, wedgeprops=dict(width=0.45, edgecolor='w') ) # 计算Top-N特征占总特征重要性的比例 subset_importance_ratio = top_n_features['Importance'].sum() / df_importance['Importance'].sum() # 在甜甜圈中心添加文本 ax_inset.text(0, 0, f'Top {N_DONUT_FEATURES} 特征\n占总重要性\n{subset_importance_ratio:.2%}', ha='center', va='center', fontsize=9, linespacing=1.4) label_threshold = 3.0 # 设置标签显示的阈值,小于此值的百分比会用引导线引出 y_text_offsets = {'left': 1.4, 'right': 1.4} # 初始化引导线标签的垂直偏移量 # 为每个扇区添加百分比标签 for i, p in enumerate(wedges): percent = donut_percentages.iloc[i] ang = (p.theta2 - p.theta1) / 2. + p.theta1 # 计算扇区中心角度 y = np.sin(np.deg2rad(ang)) # 计算标签的y坐标 x = np.cos(np.deg2rad(ang)) # 计算标签的x坐标 # 如果百分比小于阈值,使用引导线 if percent < label_threshold and percent > 0: side = 'right' if x > 0 else 'left' # 判断标签在左侧还是右侧 y_pos = y_text_offsets[side] # 获取当前侧的y偏移 y_text_offsets[side] += -0.2 if y > 0 else 0.2 # 更新偏移量,避免标签重叠 connectionstyle = f"angle,angleA=0,angleB={ang}" # 设置引导线样式 # 添加带引导线的注释 ax_inset.annotate(f'{percent:.1f}%', xy=(x, y), xytext=(0.2 * np.sign(x), y_pos), fontsize=9, ha='center', arrowprops=dict(arrowstyle="-", connectionstyle=connectionstyle, relpos=(0.5, 0.5))) # 如果百分比大于阈值,直接在扇区内显示 elif percent > 0: ax_inset.text(x * 0.8, y * 0.8, f'{percent:.1f}%', ha='center', va='center', fontsize=9, fontweight='bold', color='white') # 在甜甜圈图右侧添加图例 ax_inset.legend(wedges, donut_feature_names, loc="center left", bbox_to_anchor=(1.2, 0.5), frameon=False, fontsize=11) plt.savefig(save_path, dpi=720, bbox_inches='tight') # 保存高分辨率图表 plt.close(fig) # 关闭图表,释放内存 # 定义一个函数,用于绘制残差图 def plot_residuals_styled(residuals, y_pred, save_path, title): """ 绘制残差与预测值的关系图,并高亮显示异常值。 residuals: 残差 (真实值 - 预测值) y_pred: 预测值 save_path: 图片保存路径 title: 图表标题 """ plt.style.use('seaborn-v0_8-whitegrid') # 使用预设绘图风格 plt.rc("font", family='Microsoft YaHei') # 设置中文字体 fig, ax = plt.subplots(figsize=(10, 8)) # 创建一个10x8英寸的画布 sd_residuals = np.std(residuals) # 计算残差的标准差 is_outlier = np.abs(residuals) > 2 * sd_residuals # 定义异常值:绝对残差大于2倍标准差 num_outliers = np.sum(is_outlier) # 计算异常值的数量 print(f"在数据集 '{title}' 中, 共找到 {num_outliers} 个异常值 (残差 > 2 S.D.)。") # 打印异常值信息 sd_label = f'S.D. (±{sd_residuals:.2f})' # 准备标准差区间的图例标签 ax.axhspan(-sd_residuals, sd_residuals, color='yellow', alpha=0.3, label=sd_label) # 绘制一个表示一个标准差范围的水平区域 # 绘制正常值的散点图 ax.scatter(y_pred[~is_outlier], residuals[~is_outlier], alpha=0.6, c='green', edgecolors='k', linewidth=0.5, s=50, label='正常值') # 绘制异常值的散点图 ax.scatter(y_pred[is_outlier], residuals[is_outlier], alpha=0.8, c='red', edgecolors='k', linewidth=0.5, s=70, label='异常值 (> 2 S.D.)') ax.axhline(0, color='black', linestyle='--', linewidth=1.5) # 绘制残差为0的参考线 ax.set_title(title, fontsize=16, weight='bold') # 设置标题 ax.set_xlabel('预测值', fontsize=14) # 设置x轴标签 ax.set_ylabel('残差 (真实值 - 预测值)', fontsize=14) # 设置y轴标签 # 设置图表边框样式 for spine in ax.spines.values(): spine.set_visible(True) spine.set_color('black') spine.set_linewidth(1) ax.legend(loc='upper right', fontsize=12) # 显示图例 y_max = np.max(np.abs(residuals)) * 1.2 # 计算y轴的范围 ax.set_ylim(-y_max, y_max) # 设置y轴范围 plt.tight_layout() # 调整布局,防止标签重叠 plt.savefig(save_path, dpi=300, bbox_inches='tight') # 保存图表 plt.close() # 关闭图表 # ========================================================================= # ======================= 新增:手动PDP计算与绘图函数 ======================= # ========================================================================= def manual_pdp_1d(model, X_data, feature_name, grid_resolution=50): """ 手动计算一维部分依赖(PDP)和个体条件期望(ICE)数据。 返回: - grid_values: 特征的网格点。 - pdp_values: 对应的PDP值 (ICE的均值)。 - ice_lines: 所有样本的ICE线数据。 """ # 在特征的最小值和最大值之间生成一系列网格点 grid_values = np.linspace(X_data[feature_name].min(), X_data[feature_name].max(), grid_resolution) # 初始化一个数组来存储每个样本的ICE线数据 ice_lines = np.zeros((len(X_data), grid_resolution)) # 遍历数据集中每一个样本 for i, (_, sample) in enumerate(X_data.iterrows()): # 创建一个临时DataFrame,行数为网格点数,内容为当前样本的重复 temp_df = pd.DataFrame([sample] * grid_resolution) # 将要分析的特征列替换为网格值 temp_df[feature_name] = grid_values # 使用模型进行预测,得到这个样本在不同特征值下的预测结果,即ICE线 ice_lines[i, :] = model.predict(temp_df) # PDP是所有ICE线的平均值,在每个网格点上求均值 pdp_values = np.mean(ice_lines, axis=0) # 返回计算结果 return grid_values, pdp_values, ice_lines def manual_pdp_2d(model, X_data, features_tuple, grid_resolution=20): """ 手动计算二维部分依赖(PDP)数据。 返回: - grid_1: 第一个特征的网格点。 - grid_2: 第二个特征的网格点。 - pdp_values: 二维网格上对应的PDP值。 """ feat1_name, feat2_name = features_tuple # 获取两个特征的名称 # 为第一个特征生成网格点 grid_1 = np.linspace(X_data[feat1_name].min(), X_data[feat1_name].max(), grid_resolution) # 为第二个特征生成网格点 grid_2 = np.linspace(X_data[feat2_name].min(), X_data[feat2_name].max(), grid_resolution) # 初始化一个二维数组来存储PDP值 pdp_values = np.zeros((grid_resolution, grid_resolution)) # 遍历二维网格的每一个点 for i, val1 in enumerate(grid_1): for j, val2 in enumerate(grid_2): # 创建一个原始数据的临时副本 X_temp = X_data.copy() # 将第一个特征的所有值都设为当前的网格点值 X_temp[feat1_name] = val1 # 将第二个特征的所有值都设为当前的网格点值 X_temp[feat2_name] = val2 # 对修改后的整个数据集进行预测 preds = model.predict(X_temp) # 计算预测结果的平均值,作为该网格点的PDP值 pdp_values[j, i] = np.mean(preds) # 返回计算结果 return grid_1, grid_2, pdp_values def plot_3d_scatter_three_features(X_data, y_pred, features_tuple, save_path): """ 绘制三个特征的3D散点图,并用预测值对散点进行着色。 """ feat1_name, feat2_name, feat3_name = features_tuple # 获取三个特征的名称 fig = plt.figure(figsize=(12, 9)) # 创建一个12x9英寸的画布 ax = fig.add_subplot(111, projection='3d') # 添加一个3D子图 # 绘制3D散点图,x,y,z轴分别是三个特征的值,颜色c由模型预测值决定 sc = ax.scatter( X_data[feat1_name], X_data[feat2_name], X_data[feat3_name], c=y_pred, cmap='viridis', s=30, alpha=0.7, edgecolor='k', linewidth=0.5 ) ax.set_xlabel(f'{feat1_name} (标准化值)', fontsize=10, labelpad=10) # 设置x轴标签 ax.set_ylabel(f'{feat2_name} (标准化值)', fontsize=10, labelpad=10) # 设置y轴标签 ax.set_zlabel(f'{feat3_name} (标准化值)', fontsize=10, labelpad=10, rotation=180) # 设置z轴标签 ax.set_title(f'三特征3D散点图\n({feat1_name}, {feat2_name}, {feat3_name})', fontsize=14) # 设置标题 # 添加颜色条,并设置标签 cbar = fig.colorbar(sc, shrink=0.5, aspect=20, label='模型预测值', pad=0.1) ax.view_init(elev=20, azim=45) # 设置3D视图的角度 plt.savefig(save_path, dpi=300) # 保存图表 plt.close(fig) # 关闭图表 print(f"成功绘制 3D 散点图 for {features_tuple}") # 打印成功信息 def plot_3d_pdp_fixed_value(model, X_data, features, save_path, fixed_feature=None, fixed_value=None, grid_resolution=50): """ 绘制三个特征的3D PDP图,其中一个特征被固定在特定值。 """ feature_1, feature_2, feature_3 = features # 获取三个特征名称 if fixed_feature is None: # 如果没有指定要固定的特征 fixed_feature = feature_3 # 默认固定第三个特征 # 找出需要变化的两个特征 varying_features = [f for f in features if f != fixed_feature] varying_feat_1, varying_feat_2 = varying_features[0], varying_features[1] if fixed_value is None: # 如果没有指定固定的值 fixed_value = X_data[fixed_feature].mean() # 默认使用该特征的平均值 # 为两个变化的特征生成网格点 feat1_vals = np.linspace(X_data[varying_feat_1].min(), X_data[varying_feat_1].max(), grid_resolution) feat2_vals = np.linspace(X_data[varying_feat_2].min(), X_data[varying_feat_2].max(), grid_resolution) XX, YY = np.meshgrid(feat1_vals, feat2_vals) # 创建二维网格 # 使用数据集中所有特征的平均值作为背景行,以减少其他特征的影响 background_row = X_data.mean().to_dict() # 创建一个包含网格点组合的DataFrame grid_data = pd.DataFrame(np.c_[XX.ravel(), YY.ravel()], columns=varying_features) # 创建一个用于预测的网格DataFrame,以背景行作为基础 X_grid = pd.DataFrame([background_row] * len(grid_data)) # 将变化的特征列替换为网格值 X_grid[varying_feat_1] = grid_data[varying_feat_1].values X_grid[varying_feat_2] = grid_data[varying_feat_2].values # 将固定的特征列设置为指定的值 X_grid[fixed_feature] = fixed_value X_grid = X_grid[X_data.columns] # 确保列顺序与训练时一致 preds = model.predict(X_grid).reshape(XX.shape) # 进行预测,并重塑为网格形状 plt.rc("font", family='Microsoft YaHei') # 设置中文字体 fig = plt.figure(figsize=(12, 9)) # 创建画布 ax = fig.add_subplot(111, projection='3d') # 创建3D子图 # 绘制3D曲面图 surface = ax.plot_surface(XX, YY, preds, cmap='viridis', alpha=0.9, edgecolor='k', linewidth=0.2) fig.colorbar(surface, ax=ax, shrink=0.6, aspect=20, label='模型预测值') # 添加颜色条 ax.set_xlabel(f'{varying_feat_1} (标准化值)', fontsize=10, labelpad=10) # 设置x轴标签 ax.set_ylabel(f'{varying_feat_2} (标准化值)', fontsize=10, labelpad=10) # 设置y轴标签 ax.set_zlabel('模型预测值', fontsize=10, labelpad=10, rotation=90) # 设置z轴标签 # 设置标题 title_text = f'3D依赖图: {varying_feat_1} vs {varying_feat_2}\n固定 {fixed_feature} = {fixed_value:.3f}' ax.set_title(title_text, fontsize=14) ax.view_init(elev=25, azim=-120) # 设置视角 plt.savefig(save_path, dpi=300) # 保存图片 plt.close(fig) # 关闭图表 print(f"成功绘制 固定值3D PDP for {features},固定 {fixed_feature}") # 打印成功信息 print('-------------------------------------准备数据---------------------------------------') # 从指定的Excel文件中读取数据 df = pd.read_excel(r'D:\巢湖流域.xlsx') y = df.iloc[:, 0] # 提取第一列作为目标变量y x = df.iloc[:, 1:] # 提取从第二列开始的所有列作为特征变量x feature_names_from_df = x.columns.tolist() # 获取特征名称列表 print('-------------------------------------划分数据集---------------------------------------') # 将数据集划分为训练集和测试集,测试集占30%,设置随机种子以保证结果可复现 x_train, x_test, y_train, y_test = train_test_split(x, y, test_size=0.3, random_state=12) print('-------------------------------------数据标准化---------------------------------------') scaler = StandardScaler() # 实例化一个StandardScaler对象 # 对训练集进行拟合和转换,并将结果转换回DataFrame X_train_scaled_df = pd.DataFrame(scaler.fit_transform(x_train), columns=x_train.columns, index=x_train.index) # 使用在训练集上学习到的参数对测试集进行转换 X_test_scaled_df = pd.DataFrame(scaler.transform(x_test), columns=x_test.columns, index=x_test.index) print('-------------------------------------定义XGBoost模型超参数范围---------------------------------------') # 定义要进行网格搜索的XGBoost超参数范围 xgb_param_grid = { 'n_estimators': range(50, 151, 50), # 树的数量:100, 200, 300 'max_depth': range(3, 7, 1), # 树的最大深度:3, 4, 5, 6 'learning_rate': [0.01, 0.1, 0.2] # 学习率 } print('-------------------------------------搜索最佳超参数---------------------------------------') # 实例化GridSearchCV对象,用于自动寻找最佳超参数组合 gd = GridSearchCV(estimator=xgb.XGBRegressor(objective='reg:squarederror', seed=0), # 使用XGBoost回归器 param_grid=xgb_param_grid, # 指定超参数网格 cv=5, # 使用5折交叉验证 n_jobs=-1, # 使用所有可用的CPU核心进行并行计算 verbose=0) # 不输出详细的搜索过程信息 gd.fit(X_train_scaled_df, y_train) # 在标准化的训练集上执行网格搜索 print('-------------------------------------输出最佳模型---------------------------------------') print("在交叉验证中验证的最好结果:", gd.best_score_) # 打印交叉验证中的最佳得分(R2) print("最好的参数模型:", gd.best_estimator_) # 打印具有最佳参数的模型对象 print("(dict)最佳参数:", gd.best_params_) # 打印最佳参数组合的字典 print('-------------------------------------保存最佳模型---------------------------------------') model_save_dir = r'D:\新建文件夹' # 定义模型保存的目录 os.makedirs(model_save_dir, exist_ok=True) # 创建目录,如果目录已存在则不报错 model_path = os.path.join(model_save_dir, 'XGBoost_model_final.joblib') # 定义模型的完整保存路径 joblib.dump(gd.best_estimator_, model_path) # 将找到的最佳模型保存到文件 print(f"模型已保存至: {model_path}") # 打印保存成功信息 loaded_model = joblib.load(model_path) # 从文件加载模型 print('-------------------------------应用模型--------------------------------------') y_test_pred = loaded_model.predict(X_test_scaled_df) # 使用加载的模型对测试集进行预测 y_train_pred = loaded_model.predict(X_train_scaled_df) # 使用加载的模型对训练集进行预测 #保存数据 X_train_scaled_df.to_excel("xtr.xlsx") X_test_scaled_df.to_excel("xte.xlsx") pd.DataFrame([y_train,y_train_pred]).T.to_excel('ytr.xlsx') pd.DataFrame([y_train,y_test_pred]).T.to_excel('yte.xlsx') print('-------------------------------------训练模型性能---------------------------------------') train_mse = mean_squared_error(y_train, y_train_pred) # 计算训练集的均方误差(MSE) train_rmse = np.sqrt(train_mse) # 计算训练集的均方根误差(RMSE) train_mae = mean_absolute_error(y_train, y_train_pred) # 计算训练集的平均绝对误差(MAE) train_r2 = r2_score(y_train, y_train_pred) # 计算训练集的决定系数(R2) print(f'MSE: {train_mse:.4f}, RMSE: {train_rmse:.4f}, MAE: {train_mae:.4f}, R2: {train_r2:.4f}') print('-------------------------------------验证模型性能---------------------------------------') test_mse = mean_squared_error(y_test, y_test_pred) # 计算测试集的均方误差(MSE) test_rmse = np.sqrt(test_mse) # 计算测试集的均方根误差(RMSE) test_mae = mean_absolute_error(y_test, y_test_pred) # 计算测试集的平均绝对误差(MAE) test_r2 = r2_score(y_test, y_test_pred) # 计算测试集的决定系数(R2) print(f'MSE: {test_mse:.4f}, RMSE: {test_rmse:.4f}, MAE: {test_mae:.4f}, R2: {test_r2:.4f}') print('----------------------------------------结果绘图-----------------------------------------') results_plot_save_dir = r'D:\新建文件夹' # 定义结果图保存的目录 train_path = os.path.join(results_plot_save_dir, 'XGBoost_训练集精度_final.png') # 训练集拟合图的保存路径 test_path = os.path.join(results_plot_save_dir, 'XGBoost_验证集精度_final.png') # 验证集拟合图的保存路径 # 调用函数绘制训练集的拟合图 plot_regression_fit(y_train, y_train_pred, train_r2, train_rmse, train_mae, 'Train Set', 'XGBoost Model Performance (Train Set)', train_path) # 调用函数绘制测试集的拟合图 plot_regression_fit(y_test, y_test_pred, test_r2, test_rmse, test_mae, 'Test Set', 'XGBoost Model Performance (Test Set)', test_path) plt.rcdefaults() # 恢复matplotlib的默认设置 print( '----------------------------------------计算并绘制XGBoost原生特征重要性图-----------------------------------------') importances = loaded_model.feature_importances_ # 获取XGBoost模型内置的特征重要性(基于分裂增益) # 创建一个包含特征名称和重要性分数的DataFrame gbdt_importance_df = pd.DataFrame({'Feature': feature_names_from_df, 'Importance': importances}) save_path_gbdt = os.path.join(results_plot_save_dir, 'XGBoost_特征重要性组合图_final.png') # 定义保存路径 # 调用函数绘制组合特征重要性图 plot_importance_combined(gbdt_importance_df, 'XGBoost模型计算的特征重要性', save_path_gbdt, bar_color='dodgerblue') print( "----------------------------------------计算并绘制Permutation Importance图-----------------------------------------") scores = defaultdict(list) # 创建一个默认值为列表的字典,用于存储每个特征的置换重要性分数 # 遍历每一个特征 for feat_name in feature_names_from_df: X_t = X_test_scaled_df.copy() # 复制一份测试集数据 # 随机打乱当前特征列的顺序 X_t[feat_name] = np.random.permutation(X_t[feat_name].values) # 计算打乱后模型的R2分数 shuff_acc = r2_score(y_test, loaded_model.predict(X_t)) # 计算重要性:(原始R2 - 打乱后R2) / 原始R2,如果原始R2接近0则直接用差值 scores[feat_name].append((test_r2 - shuff_acc) / test_r2 if test_r2 > 1e-6 else test_r2 - shuff_acc) # 对特征按重要性得分从高到低排序 sorted_scores = sorted([(np.mean(score_list), feat) for feat, score_list in scores.items()], reverse=True) perm_feature_names = [feat for _, feat in sorted_scores] # 获取排序后的特征名称 perm_feature_scores = [score for score, _ in sorted_scores] # 获取排序后的重要性分数 # 创建一个包含置换重要性结果的DataFrame perm_importance_df = pd.DataFrame({'Feature': perm_feature_names, 'Importance': perm_feature_scores}) save_path_perm = os.path.join(results_plot_save_dir, 'XGBoost_特征重要性_Permutation_final.png') # 定义保存路径 # 调用函数绘制组合特征重要性图(使用置换重要性数据) plot_importance_combined(perm_importance_df, '特征重要性 (Permutation Importance for XGBoost)', save_path_perm, bar_color='lightcoral') print('----------------------------------------绘制残差分析图-----------------------------------------') train_residuals = y_train - y_train_pred # 计算训练集的残差 test_residuals = y_test - y_test_pred # 计算测试集的残差 train_res_path = os.path.join(results_plot_save_dir, 'XGBoost_训练集残差分析图_final.png') # 训练集残差图保存路径 test_res_path = os.path.join(results_plot_save_dir, 'XGBoost_验证集残差分析图_final.png') # 测试集残差图保存路径 # 调用函数绘制训练集残差图 plot_residuals_styled(train_residuals, y_train_pred, train_res_path, 'XGBoost 训练集残差分析') # 调用函数绘制测试集残差图 plot_residuals_styled(test_residuals, y_test_pred, test_res_path, 'XGBoost 验证集残差分析') # ================================================================================= # ============ 【全新】使用手动计算方法绘制 PDP 和 ICE 相关图 ============ # ================================================================================= print('------------------------开始 PDP 和 ICE 相关绘图 (手动实现)------------------------') # 定义PDP/ICE图的保存目录 pdp_ice_save_dir = os.path.join(results_plot_save_dir, 'XGBoost_PDP_ICE_Plots_final') os.makedirs(pdp_ice_save_dir, exist_ok=True) # 创建目录 # 定义双变量PDP图的保存目录 pdp_2way_save_dir = os.path.join(pdp_ice_save_dir, '2Way_PDP_All_Combinations') os.makedirs(pdp_2way_save_dir, exist_ok=True) # 创建目录 # 定义3D PDP图的保存目录 pdp_3d_save_dir = os.path.join(pdp_ice_save_dir, '3D_PDP_All_Combinations') os.makedirs(pdp_3d_save_dir, exist_ok=True) # 创建目录 n_top_features_for_pdp = 6 # 设置用于PDP分析的最重要特征的数量 if n_top_features_for_pdp > len(feature_names_from_df): # 如果特征总数不足,则取全部特征 n_top_features_for_pdp = len(feature_names_from_df) # 根据XGBoost原生重要性排序,选取最重要的N个特征 top_features_pdp_names = gbdt_importance_df['Feature'].tolist()[:n_top_features_for_pdp] plt.style.use('seaborn-v0_8-whitegrid') # 设置绘图风格 plt.rc("font", family='Microsoft YaHei') # 设置中文字体 # --- 1. 绘制单变量 PDP (含置信区间) 和 ICE 组合图 --- print("\n开始绘制单变量 PDP (含95%置信区间) 和 ICE 组合图...") # 遍历最重要的N个特征 for feature_name in top_features_pdp_names: print(f"正在计算特征 '{feature_name}' 的PDP/ICE数据...") try: # 使用手动编写的函数计算1D PDP和ICE数据 grid_vals, pdp_vals, ice_lines_vals = manual_pdp_1d(loaded_model, X_train_scaled_df, feature_name) # 在每个网格点上计算所有ICE线的标准差,用于构建置信区间 pdp_std = np.std(ice_lines_vals, axis=0) # 开始绘图 fig, ax = plt.subplots(figsize=(10, 8)) # 绘制所有样本的ICE线 (半透明蓝色细线) for ice_line in ice_lines_vals: ax.plot(grid_vals, ice_line, color='tab:blue', alpha=0.05, linewidth=0.5) # 绘制PDP线 (红色虚线),代表平均效应 ax.plot(grid_vals, pdp_vals, color='red', linestyle='--', linewidth=3, label='平均效应 (PDP)') # 绘制95%置信区间 (平均值 ± 1.96 * 标准差) ax.fill_between( grid_vals, pdp_vals - 1.96 * pdp_std, pdp_vals + 1.96 * pdp_std, color='skyblue', alpha=0.4, label='95% 置信区间' ) ax.set_title(f'PDP/ICE 组合图\n特征: {feature_name}', fontsize=16) # 设置标题 ax.set_xlabel(f'{feature_name} (标准化值)', fontsize=12) # 设置x轴标签 ax.set_ylabel('对预测值的依赖性', fontsize=12) # 设置y轴标签 ax.legend() # 显示图例 # 保存图表 plt.savefig(os.path.join(pdp_ice_save_dir, f'XGBoost_Manual_PDP_ICE_{feature_name}.png'), dpi=300, bbox_inches='tight') plt.close(fig) # 关闭图表 print(f"成功绘制特征 '{feature_name}' 的PDP/ICE图。") except Exception as e: print(f"绘制手动 PDP/ICE for {feature_name} 出错: {e}") # 打印错误信息 # --- 2. 绘制双变量 (2D 和 3D) PDP 图 --- print("\n开始绘制双变量 PDP (2D 热力图 和 3D 曲面图)...") if len(top_features_pdp_names) >= 2: # 确保至少有两个特征可以进行组合 # 遍历最重要的N个特征中的所有两两组合 for feat1, feat2 in combinations(top_features_pdp_names, 2): print(f"正在计算特征对 '{feat1}' vs '{feat2}' 的2D PDP数据...") try: # 使用手动编写的函数计算2D PDP数据 grid_x, grid_y, pdp_z = manual_pdp_2d(loaded_model, X_train_scaled_df, (feat1, feat2)) # 创建用于绘图的网格坐标 XX, YY = np.meshgrid(grid_x, grid_y) # 注意:pdp_z的维度可能需要转置以匹配meshgrid的坐标系 ZZ = pdp_z.T # 绘制 2D 热力图 fig_2d, ax_2d = plt.subplots(figsize=(8, 7)) # 使用contourf填充等值线图 c = ax_2d.contourf(XX, YY, ZZ, cmap='viridis', levels=20) fig_2d.colorbar(c, ax=ax_2d, label='部分依赖值') # 添加颜色条 ax_2d.set_title(f'2D PDP: {feat1} vs {feat2}', fontsize=16) # 设置标题 ax_2d.set_xlabel(f'{feat1} (标准化值)', fontsize=12) # 设置x轴标签 ax_2d.set_ylabel(f'{feat2} (标准化值)', fontsize=12) # 设置y轴标签 plt.savefig(os.path.join(pdp_2way_save_dir, f'XGBoost_Manual_PDP_2D_{feat1}_{feat2}.png'), dpi=300) # 保存 plt.close(fig_2d) # 关闭图表 # 绘制 3D 曲面图 fig_3d = plt.figure(figsize=(12, 9)) ax_3d = fig_3d.add_subplot(111, projection='3d') # 创建3D子图 # 绘制3D曲面 surf = ax_3d.plot_surface(XX, YY, ZZ, cmap='viridis', edgecolor='none', antialiased=True) fig_3d.colorbar(surf, shrink=0.5, aspect=20, label='部分依赖值', pad=0.1) # 添加颜色条 ax_3d.set_xlabel(f'{feat1} (标准化值)', fontsize=10, labelpad=10) # x轴标签 ax_3d.set_ylabel(f'{feat2} (标准化值)', fontsize=10, labelpad=10) # y轴标签 ax_3d.set_zlabel('对预测值的依赖性 (PDP)', fontsize=10, labelpad=10, rotation=180) # z轴标签 ax_3d.set_title(f'三维部分依赖图 (3D PDP)\n{feat1} vs {feat2}', fontsize=14) # 标题 ax_3d.view_init(elev=20, azim=45) # 设置视角 plt.savefig(os.path.join(pdp_3d_save_dir, f'XGBoost_Manual_PDP_3D_{feat1}_{feat2}.png'), dpi=300) # 保存 plt.close(fig_3d) # 关闭图表 print(f"成功绘制特征对 '{feat1}' vs '{feat2}' 的2D和3D PDP图。") except Exception as e: print(f"绘制手动 2D/3D PDP for {feat1} & {feat2} 出错: {e}") # 打印错误信息 # --- 绘制三特征3D散点图 --- print("\n开始绘制三特征 (3D) 散点图...") pdp_3d_scatter_save_dir = os.path.join(pdp_ice_save_dir, '3D_Scatter_Three_Features') # 定义保存目录 os.makedirs(pdp_3d_scatter_save_dir, exist_ok=True) # 创建目录 if len(top_features_pdp_names) >= 3: # 确保至少有3个特征 # 最多选择前4个重要特征进行组合,避免组合数过多 n_features_for_3d_scatter = min(len(top_features_pdp_names), 4) # 遍历所有三个特征的组合 for features_tuple in combinations(top_features_pdp_names[:n_features_for_3d_scatter], 3): try: # 定义保存路径 save_path = os.path.join(pdp_3d_scatter_save_dir, f'XGBoost_3D_Scatter_{features_tuple[0]}_{features_tuple[1]}_{features_tuple[2]}.png') # 调用函数绘制3D散点图 plot_3d_scatter_three_features(X_test_scaled_df, y_test_pred, features_tuple, save_path) except Exception as e: print(f"绘制 3D 散点图 for {features_tuple} 出错: {e}") # 打印错误信息 # --- 调用:绘制固定特征值的3D PDP图 --- print("\n开始绘制固定特征值的3D PDP图...") pdp_3d_fixed_save_dir = os.path.join(pdp_ice_save_dir, '3D_PDP_Fixed_Value') # 定义保存目录 os.makedirs(pdp_3d_fixed_save_dir, exist_ok=True) # 创建目录 if len(top_features_pdp_names) >= 3: # 确保至少有3个特征 # 最多选择前4个重要特征进行组合 n_features_for_3d_fixed = min(len(top_features_pdp_names), 4) # 遍历所有三个特征的组合 for features_tuple in combinations(top_features_pdp_names[:n_features_for_3d_fixed], 3): # 对每个组合,轮流固定其中的一个特征 for feature_to_fix in features_tuple: try: features_list = list(features_tuple) # 元组转列表 # 获取另外两个变化的特征 varying_feats = [f for f in features_list if f != feature_to_fix] # 定义保存路径 save_path = os.path.join(pdp_3d_fixed_save_dir, f'XGBoost_3DPDP_{varying_feats[0]}_{varying_feats[1]}_Fix_{feature_to_fix}.png') # 将固定的值设为该特征的中位数 fixed_val = X_train_scaled_df[feature_to_fix].median() # 调用函数绘制固定特征值的3D PDP图 plot_3d_pdp_fixed_value( loaded_model, X_train_scaled_df, features_list, save_path, fixed_feature=feature_to_fix, fixed_value=fixed_val ) except Exception as e: print(f"绘制固定值3D PDP for {features_list} (固定 {feature_to_fix}) 出错: {e}") # 打印错误信息 print('------------------------开始 SHAP 分析------------------------') shap_save_dir = os.path.join(results_plot_save_dir, 'XGBoost_SHAP_Plots_final') # 定义SHAP图的保存目录 os.makedirs(shap_save_dir, exist_ok=True) # 创建目录 explainer = shap.TreeExplainer(loaded_model) # 为树模型创建一个SHAP解释器 shap_values = explainer(X_test_scaled_df) # 计算测试集所有样本的SHAP值 print("\n绘制 SHAP Summary Plot (条形图)...") # 计算每个特征的平均绝对SHAP值,作为其重要性 shap_importance_vals = np.abs(shap_values.values).mean(axis=0) # 创建包含SHAP重要性的DataFrame shap_importance_df = pd.DataFrame({'Feature': X_test_scaled_df.columns, 'Importance': shap_importance_vals}) save_path_shap = os.path.join(shap_save_dir, 'XGBoost_SHAP_特征重要性组合图_final.png') # 定义保存路径 # 调用组合重要性绘图函数,绘制SHAP重要性条形图 plot_importance_combined(shap_importance_df, 'SHAP 特征重要性 (平均绝对SHAP值)', save_path_shap, bar_color='#007bff') print("绘制 SHAP Summary Plot (散点分布图)...") shap.summary_plot(shap_values, X_test_scaled_df, show=False) # 生成SHAP摘要图(散点形式) plt.title('SHAP 特征影响概览 (散点分布)', fontsize=16) # 添加标题 plt.tight_layout() # 调整布局 plt.savefig(os.path.join(shap_save_dir, 'XGBoost_SHAP_summary_scatter.png'), dpi=300, bbox_inches='tight') # 保存 plt.close() # 关闭图表 print("绘制 SHAP Dependence Plots...") shap_dependence_save_dir = os.path.join(shap_save_dir, 'Dependence_Plots') # 定义SHAP依赖图的保存目录 os.makedirs(shap_dependence_save_dir, exist_ok=True) # 创建目录 # 为最重要的N个特征绘制SHAP依赖图 for feature_name in top_features_pdp_names: # 绘制单个特征的依赖图,图中颜色表示交互效应最强的另一个特征 shap.dependence_plot(feature_name, shap_values.values, X_test_scaled_df, interaction_index="auto", show=False) plt.gcf().suptitle(f'SHAP 依赖图: {feature_name}', fontsize=16) # 添加总标题 plt.tight_layout() # 调整布局 plt.savefig(os.path.join(shap_dependence_save_dir, f'XGBoost_SHAP_dependence_{feature_name}.png'), dpi=300, bbox_inches='tight') # 保存图表 plt.close() # 关闭图表 print("绘制 SHAP Waterfall Plot (针对测试集第一个样本)...") plt.figure() # 创建一个新的画布 # 绘制瀑布图,展示单个预测(这里是测试集第一个样本)的SHAP值构成 shap.plots.waterfall(shap_values[0], max_display=15, show=False) plt.title('SHAP Waterfall Plot (测试集样本 0)', fontsize=16) # 添加标题 plt.tight_layout() # 调整布局 plt.savefig(os.path.join(shap_save_dir, 'XGBoost_SHAP_waterfall_sample_0.png'), dpi=300, bbox_inches='tight') # 保存 plt.close() # 关闭图表 print('----------------------------------------SHAP 分析完成-----------------------------------------') print('----------------------------------------开始 ALE 分析-----------------------------------------') ale_save_dir = os.path.join(results_plot_save_dir, 'XGBoost_ALE_Plots_final') # 定义ALE图的保存目录 os.makedirs(ale_save_dir, exist_ok=True) # 创建目录 print(f"ALE 相关图将保存到: {ale_save_dir}") top_features_ale_names = top_features_pdp_names # 使用与PDP相同的最重要特征列表 print(f"\n开始为最重要的 {len(top_features_ale_names)} 个特征绘制一维 ALE 图...") # 生成一组颜色用于绘制不同的ALE图 colors = plt.cm.viridis(np.linspace(0, 0.85, len(top_features_ale_names))) # 遍历最重要的特征 for i, feature_name in enumerate(top_features_ale_names): try: # 使用PyALE库计算并绘制一维ALE图 ale_eff = ale(X=X_train_scaled_df, model=loaded_model, feature=[feature_name], feature_type='continuous', grid_size=50, include_CI=True, C=0.95) fig, ax = plt.gcf(), plt.gca() # 获取当前的图和坐标轴 current_color = colors[i] # 为当前特征选择一个颜色 if ax.lines: # 如果图中有线(ALE主线) ax.lines[0].set_color(current_color) # 设置线的颜色 ax.lines[0].set_linewidth(2.5) # 设置线的宽度 if ax.collections: # 如果图中有集合(置信区间) ax.collections[0].set_facecolor(current_color) # 设置填充颜色 ax.collections[0].set_alpha(0.2) # 设置透明度 ax.set_title(f'累积局部效应 (ALE) - 特征: {feature_name}', fontsize=16) # 设置标题 ax.set_xlabel(f'{feature_name} (标准化值)', fontsize=12) # 设置x轴标签 ax.set_ylabel('ALE (对预测值的影响)', fontsize=12) # 设置y轴标签 plt.tight_layout() # 调整布局 plt.savefig(os.path.join(ale_save_dir, f'XGBoost_ALE_1D_{feature_name}.png'), dpi=300, bbox_inches='tight') # 保存 plt.close(fig) # 关闭图表 except Exception as e: print(f"绘制 1D ALE for {feature_name} 出错: {e}") # 打印错误信息 if plt.get_fignums(): # 如果有未关闭的图表 plt.close('all') # 全部关闭 print(f"\n开始为最重要的特征对绘制二维 ALE 图...") if len(top_features_ale_names) >= 2: # 确保至少有两个特征 # 遍历所有两两特征组合 for feat1_name, feat2_name in combinations(top_features_ale_names, 2): try: # 计算二维ALE效应,但不立即绘图 (plot=False) ale_eff_2d = ale(X=X_train_scaled_df, model=loaded_model, feature=[feat1_name, feat2_name], feature_type='continuous', grid_size=30, plot=False) fig, ax = plt.subplots(figsize=(8, 7)) # 创建画布 # 使用pcolormesh绘制二维ALE热力图 im = ax.pcolormesh(ale_eff_2d.index, ale_eff_2d.columns, ale_eff_2d.values.T, cmap='viridis', shading='auto') fig.colorbar(im, ax=ax, label='ALE (对预测值的影响)') # 添加颜色条 ax.set_title(f'二维 ALE: {feat1_name} vs {feat2_name}', fontsize=16) # 设置标题 ax.set_xlabel(f'{feat1_name} (标准化值)', fontsize=12) # 设置x轴标签 ax.set_ylabel(f'{feat2_name} (标准化值)', fontsize=12) # 设置y轴标签 plt.tight_layout() # 调整布局 plt.savefig(os.path.join(ale_save_dir, f'XGBoost_ALE_2D_{feat1_name}_vs_{feat2_name}.png'), dpi=300, bbox_inches='tight') # 保存图表 plt.close(fig) # 关闭图表 except Exception as e: print(f"绘制 2D ALE for {feat1_name} & {feat2_name} 出错: {e}") # 打印错误信息 if plt.get_fignums(): # 如果有未关闭的图表 plt.close('all') # 全部关闭 print('----------------------------------------ALE 分析完成-----------------------------------------') print('----------------------------------------脚本执行完毕-----------------------------------------') 以上是我对巢湖流域西半湖湖心的国控监测站的2022/4/1 0:00:00 - 2022/7/26 16:00:00时间段的数据做的建模,根据我的代码、数据、结果图、写一篇中文论文,要求可以直接投稿期刊的结果

最新推荐

recommend-type

生成一张二维码图片,将二维码图片合成到另一张含有透明区域的图片里。.zip

生成一张二维码图片,将二维码图片合成到另一张含有透明区域的图片里。.zip
recommend-type

此库是基于 CameraX 的二维码扫描封装、仅含基础功能(扫码、闪光灯),不包含扫码框动画,如有需要请自行实现。目的是

此库是基于 CameraX 的二维码扫描封装、仅含基础功能(扫码、闪光灯),不包含扫码框动画,如有需要请自行实现。目的是解决以往原始 Camera 实现的扫码再较长屏幕设备上可能出现因画面纵向被拉伸导致识别率低的问题,相比于传统的 Camera,CameraX 的优势更大,启动速度响应速度都更快。.zip
recommend-type

Hyperledger Fabric v2与Accord Project Cicero智能合约开发指南

标题和描述中提到的“hlf-cicero-contract:Accord Project Cicero与Hyperledger Fabric v2签约”以及“半西约合同”暗示了与智能合约和区块链技术相关的知识点。下面详细说明这些知识点: ### 智能合约与区块链技术 智能合约是一套运行在区块链上的程序,当合约条款被触发时,合约会自动执行相应的操作。这种自动执行的特点使得智能合约特别适合于执行多方之间的可信交易,它能减少或消除中介服务的需要,从而降低交易成本并提高效率。 区块链技术是一种分布式账本技术,通过加密算法和共识机制保证了交易数据的不可篡改性和透明性。区块链上的每一笔交易都会被网络中的多个节点验证并记录,确保了交易记录的安全性。 ### Hyperledger Fabric v2 Hyperledger Fabric 是由Linux基金会托管的一个开源项目,它是企业级区块链框架,旨在为商业应用提供安全、模块化、可扩展的区块链平台。Hyperledger Fabric v2.2是该框架的一个版本。 Hyperledger Fabric v2支持链码(Chaincode)概念,链码是部署在Hyperledger Fabric网络上的应用程序,它可以被用来实现各种智能合约逻辑。链码在运行时与网络中的背书节点和排序服务交互,负责验证、执行交易以及维护账本状态。 ### Accord Project Cicero Accord Project Cicero 是一个开源的智能合同模板和执行引擎,它允许开发者使用自然语言来定义合同条款,并将这些合同转换为可以在区块链上执行的智能合约。CiceroMark是基于Markdown格式的一种扩展,它允许在文档中嵌入智能合约逻辑。 通过Accord Project Cicero,可以创建出易于理解、可执行的智能合约。这些合同可以与Hyperledger Fabric集成,利用其提供的安全、透明的区块链网络环境,从而使得合同条款的执行更加可靠。 ### 智能合约的安装与部署 描述中提到了“安装”和“启动”的步骤,这意味着为了使用HLF v2.2和Accord Project Cicero,需要先进行一系列的配置和安装工作。这通常包括设置环境变量(例如HLF_INSTALL_DIR)、安装区块链网络(Test-Net)以及安装其他必需的软件工具(如jq)。 jq是一个轻量级且灵活的命令行JSON处理器,常用于处理JSON数据。在区块链项目中,jq可以帮助开发者处理链码或智能合约的数据,特别是在与网络节点交互时。 ### JavaScript 标签 标签“JavaScript”表明本项目或相关文档中会涉及到JavaScript编程语言。Hyperledger Fabric v2支持多种智能合约语言,其中JavaScript是一个广泛使用的选项。JavaScript在编写链码时提供了灵活的语法和强大的库支持,是进行区块链开发的一个流行选择。 ### 文件结构 文件名称列表“hlf-cicero-contract-master”暗示这是一个包含所有相关文件和资源的项目源代码目录。这个名称通常表明开发者可以从该目录开始探索、安装和配置项目的所有组件。 ### 综合知识点 1. 智能合约与区块链技术可以自动化执行多方面可信交易,降低交易成本并提高效率。 2. Hyperledger Fabric v2为企业提供一个安全、模块化、可扩展的区块链平台。 3. Accord Project Cicero结合Markdown格式的CiceroMark,将自然语言定义的合同条款转换为可执行的智能合约。 4. 智能合约的安装和部署涉及到一系列配置步骤,包括设置环境变量、安装必要的软件工具等。 5. JavaScript是编写智能合约的流行语言之一,为区块链开发提供灵活性和强大的库支持。 6. 项目文件结构表明从一个主目录可以探索和配置所有项目相关文件和资源。 以上是根据文件标题、描述、标签以及文件名称列表所提取的相关知识点。这些知识点对于理解Hyperledger Fabric v2和Accord Project Cicero在智能合约中的应用尤为重要。
recommend-type

深度神经网络优化技巧全解析

# 深度神经网络优化技巧全解析 ## 1 超越 Sigmoid 函数 在神经网络中,Sigmoid 函数曾被广泛使用,但它存在一些问题,如梯度消失。研究人员一直在寻找更好的激活函数,且不同的激活函数在不同场景下表现各异。 ### 1.1 ReLU 函数登场 如今,修正线性单元(ReLU)成为了 Sigmoid 的常用替代函数。与 Sigmoid 相比,ReLU 非常简单,以下是其 Python 实现: ```python def relu(z): if z <= 0: return 0 else: return z ``` ReLU 由两段直
recommend-type

什么是噪声功率密度

<think> 嗯,用户这次问的是噪声功率密度的定义,结合之前的系统指令和站内引用,需要给出清晰准确的中文解释。用户可能是电子工程或通信专业的学生,正在学习噪声相关的理论基础,也可能是工程师需要实际应用概念。从引用来[^1]看,用户对相位噪声的定义有基础认知,但需要系统梳理核心概念。 噪声功率密度最本质的定义应该是单位带宽内的噪声功率。引用[^2]提到电阻热噪声的例子很典型,50Ω电阻在300K环境下功率谱密度是定值(0.9nV/√Hz)²,这说明: 1. 它描述的是噪声功率随频率分布的密度 2. 与带宽强相关(带宽加倍则总功率加倍) 3. 单位通常用W/Hz或V²/Hz 维纳-辛钦定理(
recommend-type

Libshare: Salesforce的高效可重用模块集合

Salesforce是一个云基础的CRM平台,它允许用户构建定制应用程序来满足特定的业务需求。Apex是Salesforce平台上的一个强类型编程语言,用于开发复杂的业务逻辑,通过触发器、类和组件等实现。这些组件使得开发者可以更高效地构建应用程序和扩展Salesforce的功能。 在提到的"libshare:经过测试的Salesforce可重用模块"文件中,首先介绍了一个名为Libshare的工具包。这个工具包包含了一系列已经过测试的可重用模块,旨在简化和加速Salesforce应用程序的开发。 Libshare的各个组成部分的知识点如下: 1. 设置模块:在Salesforce应用程序中,应用程序设置的管理是必不可少的一部分。设置模块提供了一种简便的方式存储应用程序的设置,并提供了一个易用的API来与之交互。这样,开发者可以轻松地为不同的环境配置相同的设置,并且可以快速地访问和修改这些配置。 2. Fluent断言模块:断言是单元测试中的关键组成部分,它们用于验证代码在特定条件下是否表现预期。Fluent断言模块受到Java世界中Assertj的启发,提供了一种更流畅的方式来编写断言。通过这种断言方式,可以编写更易于阅读和维护的测试代码,提高开发效率和测试质量。 3. 秒表模块:在性能调优和效率测试中,记录方法的执行时间是常见的需求。秒表模块为开发者提供了一种方便的方式来记录总时间,并跟踪每种方法所花费的时间。这使得开发者能够识别瓶颈并优化代码性能。 4. JsonMapper模块:随着Web API的广泛应用,JSON数据格式在应用程序开发中扮演了重要角色。JsonMapper模块为开发者提供了一个更高级别的抽象,用于读取和创建JSON内容。这能够大幅简化与JSON数据交互的代码,并提高开发效率。 5. utils模块:在软件开发过程中,经常会遇到需要重复实现一些功能的情况,这些功能可能是通用的,例如日期处理、字符串操作等。utils模块提供了一系列已经编写好的实用工具函数,可以用于节省时间,避免重复劳动,提高开发效率。 6. 记录器模块:记录器通常用于记录应用程序的运行日志,以便于问题诊断和性能监控。系统提供的System.debug功能虽然强大,但在大型应用中,统一的记录器包装器可以使得日志管理更加高效。记录器模块支持记录器名称,并且可以对日志进行适当的封装。 7. App Logger模块:App Logger模块扩展了记录器模块的功能,它允许开发者将日志语句保存到一个精心设计的App Log对象中。此外,App Logger模块支持存储长达56k字符的日志内容,这对于复杂应用的监控和调试非常有用。 8. 应用程序任务模块:在处理异步作业时,例如批量数据处理或定时任务,需要有一个框架来管理和跟踪这些任务。应用程序任务模块提供了一个框架,用于处理可排队的作业,并能够跟踪这些任务的执行情况。 通过Libshare提供的这些模块,Salesforce的开发者能够减少开发工作量,加快开发速度,并提高代码质量。这些模块能够帮助开发者避免重复的“造轮子”工作,专注于核心业务逻辑的实现。同时,由于Libshare作为托管程序包发布,开发者无需担心代码的维护和管理,只需将其添加到自己的Salesforce组织中即可使用。 Libshare的发布也强调了可重用性的重要性,这是软件工程领域中长期提倡的一个原则。通过使用可重用的组件,开发者能够遵循DRY(Don't Repeat Yourself)原则,从而减少代码的冗余,提高生产效率,同时降低因重复编写相同代码而导致错误的风险。 总之,Libshare是一个有价值的资源,对于那些希望在Salesforce平台上快速构建高效、可靠应用程序的开发者来说,这些预置的、经过测试的模块无疑是一个强大的助手。
recommend-type

机器学习技术要点与应用解析

# 机器学习技术要点与应用解析 ## 1. 机器学习基础概念 ### 1.1 数据类型与表示 在编程中,数据类型起着关键作用。Python 具有动态类型特性,允许变量在运行时改变类型。常见的数据类型转换函数包括 `bool()`、`int()`、`str()` 等。例如,`bool()` 函数可将值转换为布尔类型,`int()` 用于将值转换为整数类型。数据类型还包括列表(`lists`)、字典(`dictionaries`)、元组(`tuples`)等集合类型,其中列表使用方括号 `[]` 表示,字典使用花括号 `{}` 表示,元组使用圆括号 `()` 表示。 ### 1.2 变量与命名
recommend-type

点击歌曲没反应

<think> 我们之前已经讨论了如何将音频文件显示在QListView中,并希望实现点击播放。现在遇到的问题是点击列表项没有反应。 原因分析: 1. 我们没有将点击信号连接到播放槽函数。 2. 播放列表(QMediaPlaylist)可能没有正确添加媒体。 3. 媒体路径可能不正确。 解决方案: 按照之前的思路,我们需要做以下几步: 步骤1:确保已经创建了QMediaPlayer和QMediaPlaylist对象,并且播放器设置了播放列表。 步骤2:将QListView的点击信号(clicked)连接到自定义的槽函数,在该槽函数中设置播放列表的当前索引并播放。 步骤3:
recommend-type

SM-CNN-Torch: Torch实现短文本对排名的CNN模型

标题中提到的“SM-CNN-Torch”是一个深度学习框架Torch的实现版本,它基于Severyn和Moschitti在2015年SIGIR会议上发表的一篇论文所描述的卷积神经网络(CNN)模型。这篇论文的内容主要关注的是如何利用CNN对短文本对进行有效的排名,这一点对于问题回答(question-answering, QA)系统来说至关重要。实施该CNN模型的目标是为了更好地处理问答系统中的文本对比较问题,例如,在搜索引擎中确定哪些文档与用户的查询更加相关。 在描述中提到了如何使用该仓库中的代码。首先,用户需要安装Torch库,这是实现和运行SM-CNN-Torch模型的前提条件。接着,用户需要使用提供的脚本(fetch_and_preprocess.sh)下载并预处理GloVe(Global Vectors for Word Representation)字嵌入数据。这一数据集是预先训练好的词向量,能够将单词转换为连续的向量表示,这在深度学习模型中是处理文本的基本步骤。 在模型准备工作中,还需要注意的是Python版本,因为模型运行依赖于Python环境,建议的版本为2.7或更高版本。此外,描述中还提到了并行处理的线程数设置,这表明模型在运行过程中可能会涉及到并行计算,以加速计算过程。通过设置环境变量OMP_NUM_THREADS,可以指定并行计算时的线程数。 文件名称列表中的“SM-CNN-Torch-master”表示这是该仓库的主目录,包含了所有实现Severyn和Moschitti CNN模型的相关文件。 该存储库还包含了一些附加信息,例如,原始Torch实现已经被PyTorch版本所取代。PyTorch是Torch的一个分支,它提供了更多的功能和更易于使用的接口,对研究人员和开发者来说更加友好。此外,该仓库目前仅用于存档目的,这意味着原始的Torch代码不再被积极维护,而是作为一种历史记录保留下来。 标签“deep-learning”表明该项目是一个深度学习项目,所使用的模型是深度神经网络,特别是卷积神经网络。标签“question-answering”则直接指向了问题回答系统,这是深度学习的一个重要应用领域。标签“convolutional-neural-networks”指明了所使用的网络类型是卷积神经网络,它在图像处理和自然语言处理中都有广泛应用。而“Lua”标签则是因为Torch是用Lua语言编写的,尽管它通常与Python一起使用,但也有一个使用Lua的版本。 总的来说,SM-CNN-Torch是一个专门针对短文本对排名的深度学习模型的实现,它允许研究人员和开发者利用已经发表的研究成果来搭建和测试自己的模型,同时为了解其背后原理和实现细节提供了具体的代码和数据处理流程。
recommend-type

Python与机器学习基础入门

# Python与机器学习基础入门 ## 1. Python环境与包管理 ### 1.1 Anaconda与Miniconda Anaconda 功能丰富,自带集成开发环境(IDE)和独立于官方 Python 仓库的包仓库。若不需要这些额外功能,可选择安装 Miniconda,它仅包含 Conda 和 Python,安装包更小。 ### 1.2 Conda 与 pip 的对比 - **安装方式**:Conda 和 pip 在安装包时操作相似,例如使用 Conda 安装特定版本的 Keras 可使用命令 `conda install keras=2.2.4`。 - **功能特点**: