目次
4.1 さまざまな種類の医薬品のスペクトル データの平均曲線
4.3 各種漢方スペクトルのスペクトル情報発散 SID の計算
1. データの前処理
1.1 基本データ情報の探索
附属書1
のいくつかの医薬品の中赤外スペクトルデータに従って
、さまざまな種類の医薬品の特性と違いを研究し、医薬品の種類を特定します。
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif'] = 'SimHei' # 设置中文显示
plt.rcParams['axes.unicode_minus'] = False
data = pd.read_excel('附件1.xlsx',index_col = 0) # index_col指定索引
data.head()
data.shape # 数据维度
# (425, 3348)
data.info() # 数据基本信息
data.isnull().any().any() # 空值判断
# False
データに欠損値がないことを調べて見つける
1.2 データの視覚化
# 数据可视化
def func_1(x):
plt.plot(#####)
def func_2(data):
fontsize = 5
plt.figure(figsize=(8, 6), dpi = 300)
########
plt.yticks(fontsize = fontsize)
plt.xlabel('波数(cm^-1)')
plt.ylabel('吸光度(AU)')
plt.grid(True) # 网格线设置
data.agg(lambda x: func_1(x), axis = 1)
plt.show()
func_2(data)
視覚化の結果は、明らかに外れ値である 3 つのスペクトル データがあることを示しています。これらは、外れ値または別のクラスである可能性があります。
1.3 外れ値処理
トリプル シグマ ルールを導入して、データに外れ値があるかどうかをチェックし、外れ値インデックスを出力し、外れ値を削除して、次の医薬品の種類の識別に備えます。
#异常值检验3σ
def func_3(x):
lower = x.mean()-3*x.std()
toplimit = x.mean()+3*x.std()
return (x<lower)|(x>toplimit)
ycz = data.agg(lambda x:func_3(x))
ycz_index = data[(*******)].index
ycz_index
# Int64Index([64, 136, 201], dtype='int64', name='No')
data.drop(****,axis=0,inplace = True)
func_2(data)
data.to_excel('data_ycl.xlsx')
2. データ固有値抽出
データ抽出の特徴量は、次の医薬品の種類の識別のために準備されます
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from sklearn.decomposition import PCA
plt.rcParams['font.sans-serif'] = 'SimHei' # 设置中文显示
plt.rcParams['axes.unicode_minus'] = False
data = pd.read_excel('data_ycl.xlsx', index_col = 0)
2.1 データの標準化
# 0-1标准化
arr_max = np.max(data)
arr_min = np.min(data)
data_bzh = (data-arr_min)/(arr_max-arr_min)
data_bzh
2.2 固有値を抽出するための PCA
主成分分析による固有値の抽出
pca = PCA()
pca.fit(data_bzh)
pca.explained_####### # 贡献率
lg = np.cumsum(#####) #累计贡献率
a = [0.59843097, 0.88309499, 0.93970633, 0.97403493, 0.9853352 ,0.98891337, 0.99174341]
plt.figure(figsize=(8, 6), dpi = 300)
plt.plot(a)
plt.title('前七个主成分累计贡献率')
plt.xlabel('主成分')
plt.ylabel('累计贡献率')
plt.grid(True)
plt.savefig('前七个主成分累计贡献率.png')
plt.show()
砂利プロットからの主成分の決定
pca = PCA(3) # 选取累计贡献率大于90%的主成分(3个主成分)
pca.fit(data_bzh)
data_jw = pca.transform(data_bzh)
data_jw
3. 医薬品の種類を特定するためのデータのクラスタリング
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans
from collections import Counter
from sklearn import metrics
from mpl_toolkits.mplot3d import Axes3D
plt.rcParams['font.sans-serif'] = 'SimHei' # 设置中文显示
plt.rcParams['axes.unicode_minus'] = False
data = pd.read_excel('data_jw.xlsx',index_col = 0)
3.1 K 値を決定するためのエルボ線図
SSE = []
for k in ####:
############
km.fit(####)
SSE.append(#####)
X = range(1, 11)
plt.figure(figsize=(8, 6), dpi = 300)
plt.xlabel('k')
plt.ylabel('SSE')
plt.title('肘部图')
plt.plot(X, SSE, 'o-')
plt.grid(True)
plt.savefig('肘部图.png')
plt.show()
エルボ プロット、シルエット係数プロットを使用した k 値の決定
3.2 等高線係数マップから K 値を求める
scores = []
for k in #####:
######
score = metrics.######
scores.#######
X = range(3, 11)
plt.figure(figsize=(8, 6), dpi = 300)
plt.xlabel('k')
plt.ylabel('轮廓系数')
plt.title('轮廓系数图')
plt.plot(X, scores, 'o-')
plt.grid(True)
plt.savefig('轮廓系数图.png')
plt.show()
エルボー図によると、シルエット係数図は最終的にk値が3であると判断します
3.3 データのクラスタリング
km = KMeans(n_clusters = 3)
km.fit(data)
print(Counter(km.labels_)) # 打印每个类多少个
print(km.cluster_centers_) # 中心点
data_1 = data.reset_index() # 把索引转为列
r = pd.concat([data_1['NO'], pd.Series(km.labels_)], axis = 1)
r.columns = ['NO', '聚类类别']
print(r)
3.4 クラスタリング結果の可視化
data_lei0 = data[data['类别']==0]
data_lei1 = data[data['类别']==1]
data_lei2 = data[data['类别']==2]
x0 = data_lei0[0]
y0 = data_lei0[1]
z0 = data_lei0[2]
x1 = data_lei1[0]
y1 = data_lei1[1]
z1 = data_lei1[2]
x2 = data_lei2[0]
y2 = data_lei2[1]
z2 = data_lei2[2]
x3 = [-8.68761271, 10.22622717, -7.66566209]
y3 = [-6.26880974, -0.22269714, 7.70126935]
z3 = [0.04950984, 0.21554457, -0.43296869]
plt.figure(figsize=(8, 6), dpi = 300)
colors=['k', 'b', 'y', 'r']
ax = plt.subplot(111, projection='3d')
ax.plot(x0, y0, z0, 'o', color=colors[0], label='第一类')
ax.plot(x1, y1, z1, 'o', color=colors[1], label='第二类')
ax.plot(x2, y2, z2, 'o', color=colors[2], label='第三类')
ax.plot(x3, y3, z3, '*', color=colors[3], label='中心点')
plt.legend(loc='upper left', numpoints=1, ncol=3, fontsize=8, bbox_to_anchor=(0, 0))
plt.title('聚类效果图')
ax.set_xlabel('x')
ax.set_ylabel('y')
ax.set_zlabel('z')
plt.savefig('聚类效果图.png')
plt.show()
これにより、医薬品の種類の識別が終了します
4. さまざまな種類の医薬品の特性と違いを研究する
さまざまな種類の医薬品の特性と違いを研究する
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif'] = 'SimHei' # 设置中文显示
plt.rcParams['axes.unicode_minus'] = False
data = pd.read_excel('聚类.xlsx',index_col = 1)
data_1 = data[data['类别']=='第一类']
data_2 = data[data['类别']=='第二类']
data_3 = data[data['类别']=='第三类']
異なる種類の医薬品のスペクトルデータの平均曲線と標準偏差曲線の予備分析によると、尖度やピーク数などの特性にいくつかの違いがあることがわかります。
4.1 さまざまな種類の医薬品のスペクトル データの平均曲線
plt.figure(figsize=(8, 6), dpi = 300)
plt.xticks(range(652, 4000, 500))
plt.plot(np.mean(data_1), c = 'r', label = '第一类')
plt.plot(np.mean(data_2), c = 'b', label = '第二类')
plt.plot(np.mean(data_3), c = 'k', label = '第三类')
plt.grid(True)
plt.legend()
plt.xlabel('波数(cm^-1)')
plt.ylabel('吸光度(AU)')
plt.title('不同种类药材光谱数据均值曲线')
plt.savefig('不同种类药材光谱数据均值曲线.png')
plt.show()
4.2 各種医薬品のスペクトルデータの標準偏差曲線
plt.figure(figsize=(8, 6), dpi = 300)
plt.xticks(range(652, 4000, 500))
plt.plot(np.std(data_1), c = 'r', label = '第一类')
plt.plot(np.std(data_2), c = 'b', label = '第二类')
plt.plot(np.std(data_3), c = 'k', label = '第三类')
plt.grid(True)
plt.legend()
plt.xlabel('波数(cm^-1)')
plt.ylabel('吸光度(AU)')
plt.title('不同种类药材光谱数据标准差曲线')
plt.savefig('不同种类药材光谱数据标准差曲线.png')
plt.show()
4.3 各種漢方スペクトルのスペクトル情報発散 SID の計算
指標「スペクトル情報発散 SID」を導入して、 さまざまな種類の医薬品の特性と違いをさらに調査します
スペクトル情報発散 (SID) は、ハイパースペクトル イメージ内の 2 つの異なるピクセル間の類似性を測定するために使用されます。ユークリッド距離では、スペクトル自体の変動性が考慮されるため、スペクトル データをより適切に評価できます。
df_1 = pd.DataFrame(np.mean(data_1))
df_2 = pd.DataFrame(np.mean(data_2))
df_3 = pd.DataFrame(np.mean(data_3))
index_0 = range(652, 4000)
def SID(x, y):
p = np.zeros_like(x, dtype=np.float)
q = np.zeros_like(y, dtype=np.float)
Sid = 0
for i in range(len(x)):
p[i] = x[i]/np.sum(x)
##############
for j in range(len(x)):
#############
return Sid
# 第一类和第二类光谱信息散度(SID)
SID((pd.DataFrame(df_1.values.T, columns = index_0)).values, (pd.DataFrame(df_2.values.T, columns = index_0)).values)
# 0.024393900155562476
# 第一类和第三类光谱信息散度(SID)
SID((pd.DataFrame(df_1.values.T, columns = index_0)).values, (pd.DataFrame(df_3.values.T, columns = index_0)).values)
# 0.06295196780155943
# 第二类和第三类光谱信息散度(SID)
SID((pd.DataFrame(df_2.values.T, columns = index_0)).values, (pd.DataFrame(df_3.values.T, columns = index_0)).values)
# 0.1474926576547535