基于高光谱数据集的创新点实现-高斯核函数卷积神经网络

2024-05-29 12:28

本文主要是介绍基于高光谱数据集的创新点实现-高斯核函数卷积神经网络,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

一、高光谱数据集简介

1.1 数据集简介

数据集链接在这:高光谱数据集(.mat.csv)-科研学术
数据集包含下面三个文件:
在这里插入图片描述
文件中包含.mat与.csv,145x145x220,
其实主要使用avirissub.csv文件,在代码上只是将mat文件转成了csv文件。具体avirissub.csv如下:145x145x220,每行代表一个数据,每行前220列代表特征,最后一列代表标签值,共17类标签。
在这里插入图片描述

1.2.软件环境与配置:

安装TensorFlow2.12.0版本。指令如下:

 pip install tensorflow==2.12.0

这个版本最关键,其他库,以此安装即可。

二、基线模型实现:

该代码旨在通过构建和训练卷积神经网络(CNN)模型来进行分类任务。下面是代码的详细解释和网络模型结构的说明:

2.1. 环境设置和数据加载

import pandas as pd
from tensorflow import keras
from tensorflow.keras.layers import Dense, Dropout, Conv1D, MaxPooling1D, Flatten
from tensorflow.keras.models import Sequential
from tensorflow.keras import optimizers
from sklearn.model_selection import train_test_split
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.keras.callbacks import ModelCheckpoint, ReduceLROnPlateau
from keras.utils import np_utils
import scipy.io as sio
import osos.environ["CUDA_VISIBLE_DEVICES"] = "0"
np.random.seed(42)num_epoch = []
result_mean = []
result_std_y = []
result_std_w = []
  • 引入所需库,包括Pandas、TensorFlow、Keras、Scipy等。
  • 设置环境变量以使用指定的GPU设备。
  • 设置随机种子以确保结果可重现。

2.2. 数据加载和预处理

data = sio.loadmat('D:/python_test/data/avirissub.mat')
data_L = sio.loadmat('D:/python_test/data/avirissub_gt.mat')print(sio.whosmat('D:/python_test/data/avirissub.mat'))
print(sio.whosmat('D:/python_test/data/avirissub_gt.mat'))data_D = data['x92AV3C']
data_L = data_L['x92AV3C_gt']data_D_flat = data_D.reshape(-1, data_D.shape[-1])
print(data_D_flat.shape)data_combined = pd.DataFrame(data_D_flat)
data_combined['label'] = data_L.flatten()
data_combined.to_csv('D:/python_test/data/avirissub.csv', index=False, header=False)data = pd.read_csv('D:/python_test/data/avirissub.csv', header=None)
data = data.values
data_D = data[:, :-1]
data_L = data[:, -1]
print(data_D.shape)data_D = data_D / np.max(np.max(data_D))
data_D_F = data_D / np.max(np.max(data_D))data_train, data_test, label_train, label_test = train_test_split(data_D_F, data_L, test_size=0.8, random_state=42, stratify=data_L)data_train = data_train.reshape(data_train.shape[0], data_train.shape[1], 1)
data_test = data_test.reshape(data_test.shape[0], data_test.shape[1], 1)print(np.unique(label_train))label_train = np_utils.to_categorical(label_train,  None)
label_test = np_utils.to_categorical(label_test,  None)
  • 加载数据和标签,查看文件中的键和形状。
  • 数据预处理:将多维数据展平成二维数组,合并数据和标签,保存为CSV文件,并从CSV文件中读取数据。
  • 对特征数据进行归一化。
  • 划分训练集和测试集,并调整数据形状以与Conv1D层兼容。
  • 对标签数据进行独热编码。

2.3. 定义卷积神经网络模型

def CNN(num):result = []num_epoch.append(num)for i in range(3):time_S = time.time()model = Sequential()model.add(Conv1D(filters=6, kernel_size=8, input_shape=inputShape, activation='relu', name='spec_conv1'))model.add(MaxPooling1D(pool_size=2, name='spec_pool1'))model.add(Conv1D(filters=12, kernel_size=7, activation='relu', name='spec_conv2'))model.add(MaxPooling1D(pool_size=2, name='spec_pool2'))model.add(Conv1D(filters=24, kernel_size=8, activation='relu', name='spec_conv3'))model.add(MaxPooling1D(pool_size=2, name='spec_pool3'))model.add(Flatten(name='spe_fla'))model.add(Dense(256, activation='relu', name='spe_De'))model.add(Dense(17, activation='softmax'))adam = optimizers.Adam(learning_rate=0.001, beta_1=0.9, beta_2=0.999, epsilon=1e-8)model.compile(loss='categorical_crossentropy', optimizer=adam, metrics=['accuracy'])filepath = "../model/model_spe(5%).h5"checkpointer = ModelCheckpoint(filepath, monitor='val_acc', save_weights_only=False, mode='max', save_best_only=True, verbose=0)callback = [checkpointer]reduce_lr = ReduceLROnPlateau(monitor='val_acc', factor=0.9, patience=10, verbose=0, mode='auto', epsilon=0.000001, cooldown=0, min_lr=0)history = model.fit(data_train, label_train, epochs=num, batch_size=5, shuffle=True, validation_split=0.1, verbose=0)scores = model.evaluate(data_test, label_test, verbose=0)print("\n%s: %.2f%%" % (model.metrics_names[1], scores[1] * 100))result.append(scores[1] * 100)time_E = time.time()print("costTime:", time_E - time_S, 's')print(result)result_mean.append(np.mean(result))print("均值是:%.4f" % np.mean(result))result_std_y.append(np.std(result))print("标准差(有偏)是:%.4f" % np.std(result))result_std_w.append(np.std(result, ddof=1))print("标准差(无偏)是:%.4f" % np.std(result, ddof=1))
  • 定义CNN函数,构建并训练卷积神经网络模型。
  • 网络模型结构包括:
    • Conv1D 层:一维卷积层,用于提取特征。共三个卷积层,每层有不同的过滤器数量和卷积核大小。
    • MaxPooling1D 层:最大池化层,用于下采样。每个卷积层后都有一个池化层。
    • Flatten 层:将多维特征图展平成一维。
    • Dense 层:全连接层,包含256个神经元,激活函数为ReLU。
    • 最后一层 Dense 层:输出层,包含17个神经元,对应17个类别,激活函数为Softmax。

2.4. 模型训练和评估

if __name__ == '__main__':CNN(5)
  • 调用CNN函数并设置迭代次数为5。

完整的基线模型版本代码如下

from __future__ import print_function
import pandas as pd
from tensorflow import keras
from tensorflow.keras.layers import Dense, Dropout, Conv1D, MaxPooling1D, Flatten
from tensorflow.keras.models import Sequential
from tensorflow.keras import optimizers
from sklearn.model_selection import train_test_split
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.keras.callbacks import ModelCheckpoint, ReduceLROnPlateau
from keras.utils import np_utils
import scipy.io as sio
import os# 设置环境变量,指定使用的 GPU 设备
os.environ["CUDA_VISIBLE_DEVICES"] = "0"# 设置随机种子以便实验结果可重现
np.random.seed(42)# 初始化存储结果的列表
num_epoch = []
result_mean = []
result_std_y = []
result_std_w = []# 加载数据
data = sio.loadmat('D:/python_test/data/avirissub.mat')  # 加载数据
data_L = sio.loadmat('D:/python_test/data/avirissub_gt.mat')  # 加载标签# 查看.mat文件中包含的键和它们的形状
print(sio.whosmat('D:/python_test/data/avirissub.mat'))
print(sio.whosmat('D:/python_test/data/avirissub_gt.mat'))# 提取数据和标签
data_D = data['x92AV3C']
data_L = data_L['x92AV3C_gt']# 将多维数据展平成二维数组
data_D_flat = data_D.reshape(-1, data_D.shape[-1])
print(data_D_flat.shape)
# 将数据和标签合并
data_combined = pd.DataFrame(data_D_flat)
data_combined['label'] = data_L.flatten()# 保存为.csv文件
data_combined.to_csv('D:/python_test/data/avirissub.csv', index=False, header=False)# 从 CSV 文件中读取数据
data = pd.read_csv('D:/python_test/data/avirissub.csv', header=None)  # 14 类可以用于分类
data = data.values
data_D = data[:, :-1]  # 提取特征 提取了 data 矩阵的所有行和除了最后一列之外的所有列,这就是特征数据。
data_L = data[:, -1]  # 提取标签 提取了 data 矩阵的所有行的最后一列,这就是标签数据
print(data_D.shape)  # 打印特征数据的形状# 对特征数据进行归一化
data_D = data_D / np.max(np.max(data_D))
data_D_F = data_D / np.max(np.max(data_D))# 将数据划分为训练集和测试集
data_train, data_test, label_train, label_test = train_test_split(data_D_F, data_L, test_size=0.8, random_state=42,stratify=data_L)
# 将数据重新调整为与 Conv1D 层兼容的形状
data_train = data_train.reshape(data_train.shape[0], data_train.shape[1], 1)
data_test = data_test.reshape(data_test.shape[0], data_test.shape[1], 1)# 打印标签数据的唯一值,确保它们的范围是正确的
print(np.unique(label_train))# 根据类来自动定义独热编码
label_train = np_utils.to_categorical(label_train,  None)
label_test = np_utils.to_categorical(label_test,  None)inputShape = data_train[0].shape  # 输入形状import timedef CNN(num):result = []num_epoch.append(num)# for i in range(50):for i in range(3):time_S = time.time()model = Sequential()# 定义模型结构model.add(Conv1D(filters=6, kernel_size=8, input_shape=inputShape, activation='relu', name='spec_conv1'))model.add(MaxPooling1D(pool_size=2, name='spec_pool1'))#model.add(Conv1D(filters=12, kernel_size=7, activation='relu', name='spec_conv2'))model.add(MaxPooling1D(pool_size=2, name='spec_pool2'))#model.add(Conv1D(filters=24, kernel_size=8, activation='relu', name='spec_conv3'))model.add(MaxPooling1D(pool_size=2, name='spec_pool3'))# model.add(Conv1D(filters=48, kernel_size=10, activation='relu', name='spec_conv4'))# model.add(MaxPooling1D(pool_size=2, name='spec_pool4'))model.add(Flatten(name='spe_fla'))model.add(Dense(256, activation='relu', name='spe_De'))# model.add(Dropout(0.5,name = 'drop'))model.add(Dense(17, activation='softmax'))# 设置优化器和损失函数,并编译模型adam = optimizers.Adam(learning_rate=0.001, beta_1=0.9, beta_2=0.999, epsilon=1e-8)model.compile(loss='categorical_crossentropy', optimizer=adam, metrics=['accuracy'])filepath = "../model/model_spe(5%).h5"checkpointer = ModelCheckpoint(filepath, monitor='val_acc', save_weights_only=False, mode='max',save_best_only=True, verbose=0)callback = [checkpointer]reduce_lr = ReduceLROnPlateau(monitor='val_acc', factor=0.9, patience=10, verbose=0, mode='auto',epsilon=0.000001,cooldown=0, min_lr=0)# 训练模型并计算评分history = model.fit(data_train, label_train, epochs=num, batch_size=5, shuffle=True, validation_split=0.1,verbose=0)scores = model.evaluate(data_test, label_test, verbose=0)print("\n%s: %.2f%%" % (model.metrics_names[1], scores[1] * 100))# 保存模型result.append(scores[1] * 100)time_E = time.time()print("costTime:", time_E - time_S, 's')print(result)result_mean.append(np.mean(result))print("均值是:%.4f" % np.mean(result))result_std_y.append(np.std(result))print("标准差(有偏)是:%.4f" % np.std(result))result_std_w.append(np.std(result, ddof=1))print("标准差(无偏)是:%.4f" % np.std(result, ddof=1))if __name__ == '__main__':# 调用 CNN 函数并设置迭代次数为 50# CNN(50)CNN(5)

三、创新点实现:

这段代码在原有基础上引入了一些创新点,主要包括自定义卷积层和自定义回调函数。下面是具体创新点的详细解释:

3.1. 高斯核函数和自定义卷积层

高斯核函数
def gaussian_kernel(x, y, sigma=1.0):return tf.exp(-tf.reduce_sum(tf.square(x - y), axis=-1) / (2 * sigma ** 2))
  • 定义高斯核函数,用于计算输入片段与卷积核之间的相似性。
自定义卷积层
class GaussianKernelConv1D(Layer):def __init__(self, filters, kernel_size, sigma=1.0, **kwargs):super(GaussianKernelConv1D, self).__init__(**kwargs)self.filters = filtersself.kernel_size = kernel_sizeself.sigma = sigmadef build(self, input_shape):self.kernel = self.add_weight(name='kernel',shape=(self.kernel_size, int(input_shape[-1]), self.filters),initializer='uniform',trainable=True)super(GaussianKernelConv1D, self).build(input_shape)def call(self, inputs):output = []for i in range(inputs.shape[1] - self.kernel_size + 1):slice = inputs[:, i:i+self.kernel_size, :]slice = tf.expand_dims(slice, -1)kernel = tf.expand_dims(self.kernel, 0)similarity = gaussian_kernel(slice, kernel, self.sigma)output.append(tf.reduce_sum(similarity, axis=2))return tf.stack(output, axis=1)
  • GaussianKernelConv1D 是一个自定义的一维卷积层,使用高斯核函数来计算相似性。
  • build 方法中定义了卷积核,并设置为可训练参数。
  • call 方法中实现了卷积操作,通过滑动窗口方式计算输入片段和卷积核之间的相似性,并累加这些相似性值。

3.2. 自定义回调函数

自定义回调函数用于在每个 epoch 结束时输出训练信息
class TrainingProgressCallback(Callback):def on_epoch_end(self, epoch, logs=None):logs = logs or {}print(f"Epoch {epoch + 1}/{self.params['epochs']}, Loss: {logs.get('loss')}, Accuracy: {logs.get('accuracy')}, "f"Val Loss: {logs.get('val_loss')}, Val Accuracy: {logs.get('val_accuracy')}")
  • TrainingProgressCallback 是一个自定义回调函数,用于在每个 epoch 结束时输出训练进度,包括损失和准确率。

3.3. 模型构建、训练和评估

CNN 函数
def CNN(num):result = []num_epoch.append(num)for i in range(3):time_S = time.time()model = Sequential()# 定义模型结构model.add(GaussianKernelConv1D(filters=6, kernel_size=8, input_shape=inputShape, name='spec_conv1'))model.add(MaxPooling1D(pool_size=2, name='spec_pool1'))model.add(GaussianKernelConv1D(filters=12, kernel_size=7, name='spec_conv2'))model.add(MaxPooling1D(pool_size=2, name='spec_pool2'))model.add(GaussianKernelConv1D(filters=24, kernel_size=8, name='spec_conv3'))model.add(MaxPooling1D(pool_size=2, name='spec_pool3'))model.add(Flatten(name='spe_fla'))model.add(Dense(256, activation='relu', name='spe_De'))model.add(Dense(17, activation='softmax'))# 设置优化器和损失函数,并编译模型adam = optimizers.Adam(learning_rate=0.001, beta_1=0.9, beta_2=0.999, epsilon=1e-8)model.compile(loss='categorical_crossentropy', optimizer=adam, metrics=['accuracy'])filepath = "../model/model_spe(5%).h5"checkpointer = ModelCheckpoint(filepath, monitor='val_accuracy', save_weights_only=False, mode='max',save_best_only=True, verbose=0)callback = [checkpointer, TrainingProgressCallback()]reduce_lr = ReduceLROnPlateau(monitor='val_accuracy', factor=0.9, patience=10, verbose=0, mode='auto',min_delta=0.000001,cooldown=0, min_lr=0)callback.append(reduce_lr)# 训练模型并计算评分history = model.fit(data_train, label_train, epochs=num, batch_size=5, shuffle=True, validation_split=0.1,verbose=1, callbacks=callback)scores = model.evaluate(data_test, label_test, verbose=0)print("\n%s: %.2f%%" % (model.metrics_names[1], scores[1] * 100))result.append(scores[1] * 100)time_E = time.time()print("costTime:", time_E - time_S, 's')print(result)result_mean.append(np.mean(result))print("均值是:%.4f" % np.mean(result))result_std_y.append(np.std(result))print("标准差(有偏)是:%.4f" % np.std(result))result_std_w.append(np.std(result, ddof=1))print("标准差(无偏)是:%.4f" % np.std(result, ddof=1))
  • CNN 函数中,模型结构与之前类似,但卷积层替换为自定义的 GaussianKernelConv1D 层。
  • 使用 TrainingProgressCallback 在每个 epoch 结束时输出训练进度。
  • 训练模型并评估其性能。

四、总结

相对于原代码,新的代码主要创新点包括:

  1. 引入高斯核函数和自定义卷积层:使用高斯核函数来计算输入片段与卷积核之间的相似性,增加了模型的灵活性和非线性特征提取能力。
  2. 自定义回调函数:用于在每个 epoch 结束时输出训练进度,提供更详细的训练信息,便于实时监控和调整模型。

这篇关于基于高光谱数据集的创新点实现-高斯核函数卷积神经网络的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1013657

相关文章

大模型研发全揭秘:客服工单数据标注的完整攻略

在人工智能(AI)领域,数据标注是模型训练过程中至关重要的一步。无论你是新手还是有经验的从业者,掌握数据标注的技术细节和常见问题的解决方案都能为你的AI项目增添不少价值。在电信运营商的客服系统中,工单数据是客户问题和解决方案的重要记录。通过对这些工单数据进行有效标注,不仅能够帮助提升客服自动化系统的智能化水平,还能优化客户服务流程,提高客户满意度。本文将详细介绍如何在电信运营商客服工单的背景下进行

基于MySQL Binlog的Elasticsearch数据同步实践

一、为什么要做 随着马蜂窝的逐渐发展,我们的业务数据越来越多,单纯使用 MySQL 已经不能满足我们的数据查询需求,例如对于商品、订单等数据的多维度检索。 使用 Elasticsearch 存储业务数据可以很好的解决我们业务中的搜索需求。而数据进行异构存储后,随之而来的就是数据同步的问题。 二、现有方法及问题 对于数据同步,我们目前的解决方案是建立数据中间表。把需要检索的业务数据,统一放到一张M

关于数据埋点,你需要了解这些基本知识

产品汪每天都在和数据打交道,你知道数据来自哪里吗? 移动app端内的用户行为数据大多来自埋点,了解一些埋点知识,能和数据分析师、技术侃大山,参与到前期的数据采集,更重要是让最终的埋点数据能为我所用,否则可怜巴巴等上几个月是常有的事。   埋点类型 根据埋点方式,可以区分为: 手动埋点半自动埋点全自动埋点 秉承“任何事物都有两面性”的道理:自动程度高的,能解决通用统计,便于统一化管理,但个性化定

使用SecondaryNameNode恢复NameNode的数据

1)需求: NameNode进程挂了并且存储的数据也丢失了,如何恢复NameNode 此种方式恢复的数据可能存在小部分数据的丢失。 2)故障模拟 (1)kill -9 NameNode进程 [lytfly@hadoop102 current]$ kill -9 19886 (2)删除NameNode存储的数据(/opt/module/hadoop-3.1.4/data/tmp/dfs/na

异构存储(冷热数据分离)

异构存储主要解决不同的数据,存储在不同类型的硬盘中,达到最佳性能的问题。 异构存储Shell操作 (1)查看当前有哪些存储策略可以用 [lytfly@hadoop102 hadoop-3.1.4]$ hdfs storagepolicies -listPolicies (2)为指定路径(数据存储目录)设置指定的存储策略 hdfs storagepolicies -setStoragePo

Hadoop集群数据均衡之磁盘间数据均衡

生产环境,由于硬盘空间不足,往往需要增加一块硬盘。刚加载的硬盘没有数据时,可以执行磁盘数据均衡命令。(Hadoop3.x新特性) plan后面带的节点的名字必须是已经存在的,并且是需要均衡的节点。 如果节点不存在,会报如下错误: 如果节点只有一个硬盘的话,不会创建均衡计划: (1)生成均衡计划 hdfs diskbalancer -plan hadoop102 (2)执行均衡计划 hd

hdu1043(八数码问题,广搜 + hash(实现状态压缩) )

利用康拓展开将一个排列映射成一个自然数,然后就变成了普通的广搜题。 #include<iostream>#include<algorithm>#include<string>#include<stack>#include<queue>#include<map>#include<stdio.h>#include<stdlib.h>#include<ctype.h>#inclu

hdu1171(母函数或多重背包)

题意:把物品分成两份,使得价值最接近 可以用背包,或者是母函数来解,母函数(1 + x^v+x^2v+.....+x^num*v)(1 + x^v+x^2v+.....+x^num*v)(1 + x^v+x^2v+.....+x^num*v) 其中指数为价值,每一项的数目为(该物品数+1)个 代码如下: #include<iostream>#include<algorithm>

【C++】_list常用方法解析及模拟实现

相信自己的力量,只要对自己始终保持信心,尽自己最大努力去完成任何事,就算事情最终结果是失败了,努力了也不留遗憾。💓💓💓 目录   ✨说在前面 🍋知识点一:什么是list? •🌰1.list的定义 •🌰2.list的基本特性 •🌰3.常用接口介绍 🍋知识点二:list常用接口 •🌰1.默认成员函数 🔥构造函数(⭐) 🔥析构函数 •🌰2.list对象

【Prometheus】PromQL向量匹配实现不同标签的向量数据进行运算

✨✨ 欢迎大家来到景天科技苑✨✨ 🎈🎈 养成好习惯,先赞后看哦~🎈🎈 🏆 作者简介:景天科技苑 🏆《头衔》:大厂架构师,华为云开发者社区专家博主,阿里云开发者社区专家博主,CSDN全栈领域优质创作者,掘金优秀博主,51CTO博客专家等。 🏆《博客》:Python全栈,前后端开发,小程序开发,人工智能,js逆向,App逆向,网络系统安全,数据分析,Django,fastapi