多元散射矫正(MSC)常用于光谱的数据处理,MSC的可以消除由于在光谱测量过程中散射水平的不同(测量的位置、测量时的光线等不同光谱则有差异)带来的光谱差异,增强光谱与数据之间的相关性。该方法为了消除由于散射水平不同带来的光谱差异(即修正光谱数据的基线平移和偏移现象)需要使用“理想光谱”(光谱的变化和与样品中的成分含量满足直接的线性关系)来进行修正。由于“理想光谱”很难获得,因此在该算法中使用所有光谱数据的平均值来代替“理想光谱”。
MSC算法推导过程:
1、平均光谱: ![](https://img-blog.csdnimg.cn/20fa33ff5bca43b7b55c55be41af2ed8.png)
2、求取每个光谱和理想光谱之间的基线平移量和偏移量:
![](https://img-blog.csdnimg.cn/a7caaf64c09e42e7bfd963dc958d6945.png)
注:b就是每个光谱的平移量和偏移量,k是光谱的偏移系数
3、每个光谱减去求得的基线平移量和偏移量,得到矫正后的光谱:
![](https://img-blog.csdnimg.cn/c66e8026452c46eab1839aff9d8777a9.png)
import matplotlib.pyplot as plt
import numpy as np
import pandas as pd
#author qiaoxiaokang
def PlotSpectrum(spec): # 画图函数
plt.figure(figsize=(5, 3.2), dpi=200)
x = np.arange(900, 900 + 5 * spec.shape[1], 5)
for i in range(spec.shape[0]):
plt.plot(x, spec[i, :], linewidth=0.6)
fonts = 8
plt.xlim(700, 1800)
# plt.ylim(0, 1)
plt.xlabel('Wavelength (nm)')
plt.ylabel('absorbance (AU)')
plt.yticks(fontsize=fonts)
plt.xticks(fontsize=fonts)
plt.tight_layout(pad=0.3)
return plt
data = pd.read_excel(r'文件路径')
df = data.values
x = data.iloc[:, 1:]
y = data.iloc[:, 0]
X = x.values
Y = y.values
Y = Y.reshape((X.shape[0], 1))
X = np.array(X) # 必须要加转换成np才不会报错
Y = np.array(Y) # 必须要加转换成np才不会报错
print(Y.shape)
print(x.shape, y.shape)
pp = PlotSpectrum(X)
pp.show()
# 多元散射矫正
def msc(sdata):
n = sdata.shape[0] # 样本数量
k = np.zeros(sdata.shape[0])
b = np.zeros(sdata.shape[0])
M = np.mean(sdata, axis=0)
from sklearn.linear_model import LinearRegression
for i in range(n):
y = sdata[i, :]
y = y.reshape(-1, 1)
M = M.reshape(-1, 1)
model = LinearRegression() # 线性回归算法
model.fit(M, y)
k[i] = model.coef_
b[i] = model.intercept_ # coef_和intercept_都是模型参数,即为w coef_为w1到w4 intercept_为w0
spec_msc = np.zeros_like(sdata)
for i in range(n):
bb = np.repeat(b[i], sdata.shape[1])
kk = np.repeat(k[i], sdata.shape[1])
temp = (sdata[i, :] - bb) / kk # 求出矫正后的光谱数据
spec_msc[i, :] = temp
return spec_msc
X = msc(X)
pp = PlotSpectrum(X)
pp.show()
详细代码参考,这位大佬的文章 :(115条消息) 近红外光谱建模之光谱预处理python实现(一)_近红外python_潘旭阳的博客-CSDN博客
|