如何在光谱图中实现连续统去除?凸包优化及效果实现求助
解决方案:提取上部凸包并实现连续统去除
要解决这个问题,我们需要两步:筛选出凸包的上部边界(连续统),然后基于连续统计算去除后的光谱。以下是具体实现:
步骤1:提取上部凸包(连续统)
原始ConvexHull会生成整个凸包的所有边,包括底部的边界。我们只需要保留按波长(x轴)排序后的凸包顶点连线,这就是光谱的上包络(连续统)。
步骤2:计算连续统去除后的光谱
通过插值方法,为每个原始波长点匹配连续统对应的反射率值,再用原始反射率除以该值,得到归一化后的连续统去除光谱。
修改后的完整代码
import pandas as pd import numpy as np from scipy.spatial import ConvexHull from scipy.interpolate import interp1d import matplotlib.pyplot as plt # 读取数据 data = open('15C80D4_00002.txt') d = pd.read_table(data, sep=r'\t', header=None, names=['Wvl', 'Reflectance'], skiprows=1, engine='python') # 提取x和y数组 x = d['Wvl'].values y = d['Reflectance'].values points = np.column_stack((x, y)) # 计算凸包 hull = ConvexHull(points) # 提取凸包顶点并按波长排序(得到上部连续统的点) hull_vertices = points[hull.vertices] # 按x轴(波长)排序 hull_sorted = hull_vertices[np.argsort(hull_vertices[:, 0])] # 创建连续统插值函数,用于匹配所有原始波长点的连续统值 continuum_interp = interp1d(hull_sorted[:, 0], hull_sorted[:, 1], kind='linear') continuum = continuum_interp(x) # 计算连续统去除后的光谱(反射率/连续统) continuum_removed = y / continuum # 绘图 fig, ax = plt.subplots(figsize=(10, 6)) # 绘制原始光谱 ax.plot(x, y, label='原始光谱', color='blue', linewidth=1) # 绘制上部凸包(连续统) ax.plot(hull_sorted[:, 0], hull_sorted[:, 1], label='连续统', color='red', linestyle='--', linewidth=1.5) # 绘制连续统去除后的光谱 ax.plot(x, continuum_removed, label='连续统去除光谱', color='green', linewidth=1) # 设置图表标签和图例 ax.set_xlabel('波长') ax.set_ylabel('反射率/归一化反射率') ax.legend() plt.show()
关键代码解释
- 提取并排序凸包顶点:
hull.vertices给出凸包的顶点索引,我们将这些顶点按波长排序后,连线就是光谱的上包络,避免了底部的凸包边。 - 插值匹配连续统值:因为凸包顶点的波长数量远少于原始数据,用
interp1d做线性插值,为每个原始波长点计算对应的连续统反射率。 - 连续统去除计算:采用反射率除以连续统的方式,得到归一化后的光谱,这是连续统去除的标准方法。
内容的提问来源于stack exchange,提问作者Shivanshika Chauhan
相关产品推荐
相关产品推荐

