计算机竞赛 基于人工智能的图像分类算法研究与实现 - 深度学习卷积神经网络图像分类

news2025/1/22 22:00:56

文章目录

  • 0 简介
  • 1 常用的分类网络介绍
    • 1.1 CNN
    • 1.2 VGG
    • 1.3 GoogleNet
  • 2 图像分类部分代码实现
    • 2.1 环境依赖
    • 2.2 需要导入的包
    • 2.3 参数设置(路径,图像尺寸,数据集分割比例)
    • 2.4 从preprocessedFolder读取图片并返回numpy格式(便于在神经网络中训练)
    • 2.5 数据预处理
    • 2.6 训练分类模型
    • 2.7 模型训练效果
    • 2.8 模型性能评估
  • 3 1000种图像分类
  • 4 最后

0 简介

🔥 优质竞赛项目系列,今天要分享的是

基于人工智能的图像分类技术

该项目较为新颖,适合作为竞赛课题方向,学长非常推荐!

🧿 更多资料, 项目分享:

https://gitee.com/dancheng-senior/postgraduate

1 常用的分类网络介绍

1.1 CNN

传统CNN包含卷积层、全连接层等组件,并采用softmax多类别分类器和多类交叉熵损失函数。如下图:

在这里插入图片描述

  • 卷积层(convolution layer): 执行卷积操作提取底层到高层的特征,发掘出图片局部关联性质和空间不变性质。

  • 池化层(pooling layer): 执行降采样操作。通过取卷积输出特征图中局部区块的最大值(max-pooling)或者均值(avg-pooling)。降采样也是图像处理中常见的一种操作,可以过滤掉一些不重要的高频信息。

  • 全连接层(fully-connected layer,或者fc layer): 输入层到隐藏层的神经元是全部连接的。

  • 非线性变化: 卷积层、全连接层后面一般都会接非线性变化层,例如Sigmoid、Tanh、ReLu等来增强网络的表达能力,在CNN里最常使用的为ReLu激活函数。

  • Dropout : 在模型训练阶段随机让一些隐层节点权重不工作,提高网络的泛化能力,一定程度上防止过拟合

在CNN的训练过程总,由于每一层的参数都是不断更新的,会导致下一次输入分布发生变化,这样就需要在训练过程中花费时间去设计参数。在后续提出的BN算法中,由于每一层都做了归一化处理,使得每一层的分布相对稳定,而且实验证明该算法加速了模型的收敛过程,所以被广泛应用到较深的模型中。

1.2 VGG

VGG 模型是由牛津大学提出的(19层网络),该模型的特点是加宽加深了网络结构,核心是五组卷积操作,每两组之间做Max-
Pooling空间降维。同一组内采用多次连续的3X3卷积,卷积核的数目由较浅组的64增多到最深组的512,同一组内的卷积核数目是一样的。卷积之后接两层全连接层,之后是分类层。该模型由于每组内卷积层的不同主要分为
11、13、16、19 这几种模型

在这里插入图片描述

增加网络深度和宽度,也就意味着巨量的参数,而巨量参数容易产生过拟合,也会大大增加计算量。

1.3 GoogleNet

GoogleNet模型由多组Inception模块组成,模型设计借鉴了NIN的一些思想.

NIN模型特点:

  • 1. 引入了多层感知卷积网络(Multi-Layer Perceptron Convolution, MLPconv)代替一层线性卷积网络。MLPconv是一个微小的多层卷积网络,即在线性卷积后面增加若干层1x1的卷积,这样可以提取出高度非线性特征。
    
  • 2)设计最后一层卷积层包含类别维度大小的特征图,然后采用全局均值池化(Avg-Pooling)替代全连接层,得到类别维度大小的向量,再进行分类。这种替代全连接层的方式有利于减少参数。

Inception 结构的主要思路是怎样用密集成分来近似最优的局部稀疏结构。

在这里插入图片描述

2 图像分类部分代码实现

2.1 环境依赖

python 3.7
jupyter-notebook : 6.0.3
cudatoolkit 10.0.130
cudnn 7.6.5
tensorflow-gpu 2.0.0
scikit-learn 0.22.1
numpy
cv2
matplotlib

2.2 需要导入的包

  import os
  import cv2
  import numpy as np
  import pandas as pd
  import tensorflow as tf
  from tensorflow import keras
  from tensorflow.keras import layers,models
  from tensorflow.keras.models import Sequential
  from tensorflow.keras.optimizers import Adam
  from tensorflow.keras.callbacks import Callback
  from tensorflow.keras.utils import to_categorical
  from tensorflow.keras.applications import VGG19
  from tensorflow.keras.models import load_model
  import matplotlib.pyplot as plt
  from sklearn.preprocessing import label_binarize
  tf.compat.v1.disable_eager_execution()
  os.environ['CUDA_VISIBLE_DEVICES'] = '0' #使用GPU

2.3 参数设置(路径,图像尺寸,数据集分割比例)

 preprocessedFolder = '.\\ClassificationData\\' #预处理文件夹
 outModelFileName=".\\outModelFileName\\" 
 ImageWidth = 512
 ImageHeight = 320
 ImageNumChannels = 3
 TrainingPercent = 70  #训练集比例
 ValidationPercent = 15 #验证集比例

2.4 从preprocessedFolder读取图片并返回numpy格式(便于在神经网络中训练)

def read_dl_classifier_data_set(preprocessedFolder):
  num = 0  # 图片的总数量
  cnt_class = 0  #图片所属的类别
  label_list = []  # 存放每个图像的label,图像的类别
  img_list = []   #存放图片数据
  for directory in os.listdir(preprocessedFolder):
      tmp_dir = preprocessedFolder + directory
      cnt_class += 1
      for image in os.listdir(tmp_dir):
          num += 1
          tmp_img_filepath = tmp_dir + '\\' + image
          im = cv2.imread(tmp_img_filepath)  # numpy.ndarray
          im = cv2.resize(im, (ImageWidth, ImageHeight))  # 重新设置图片的大小
          img_list.append(im)
          label_list.append(cnt_class)  # 在标签中添加类别
          print("Picture " + str(num) + "Load "+tmp_img_filepath+"successfully")
print("共有" + str(num) + "张图片")
print("all"+str(num)+"picturs belong to "+str(cnt_class)+"classes")
return np.array(img_list),np.array(label_list)

all_data,all_label=read_dl_classifier_data_set(preprocessedFolder)

在这里插入图片描述

2.5 数据预处理

图像数据压缩, 标签数据进行独立热编码one-hot

def preprocess_dl_Image(all_data,all_label):
      all_data = all_data.astype("float32")/255  #把图像灰度值压缩到0--1.0便于神经网络训练
      all_label = to_categorical(all_label)  #对标签数据进行独立热编码
      return all_data,all_label

all_data,all_label = preprocess_dl_Image(all_data,all_label) #处理后的数据

对数据及进行划分(训练集:验证集:测试集 = 0.7:0.15:0.15)

def split_dl_classifier_data_set(all_data,all_label,TrainingPercent,ValidationPercent):
      s = np.arange(all_data.shape[0])
      np.random.shuffle(s)  #随机打乱顺序
      all_data = all_data[s] #打乱后的图像数据
      all_label = all_label[s] #打乱后的标签数据
      all_len = all_data.shape[0]
      train_len = int(all_len*TrainingPercent/100)  #训练集长度
      valadation_len = int(all_len*ValidationPercent/100)#验证集长度
      temp_len=train_len+valadation_len
      train_data,train_label = all_data[0:train_len,:,:,:],all_label[0:train_len,:] #训练集
      valadation_data,valadation_label = all_data[train_len:temp_len, : , : , : ],all_label[train_len:temp_len, : ] #验证集
      test_data,test_label = all_data[temp_len:, : , : , : ],all_label[temp_len:, : ] #测试集
      return train_data,train_label,valadation_data,valadation_label,test_data,test_label

train_data,train_label,valadation_data,valadation_label,test_data,test_label=split_dl_classifier_data_set(all_data,all_label,TrainingPercent,ValidationPercent)

2.6 训练分类模型

  • 使用迁移学习(基于VGG19)

  • epochs = 30

  • batch_size = 16

  • 使用 keras.callbacks.EarlyStopping 提前结束训练

    def train_classifier(train_data,train_label,valadation_data,valadation_label,lr=1e-4):
          conv_base = VGG19(weights='imagenet',
                  include_top=False,
                  input_shape=(ImageHeight, ImageWidth, 3) )  
          model = models.Sequential()
          model.add(conv_base)
          model.add(layers.Flatten())
          model.add(layers.Dense(30, activation='relu')) 
          model.add(layers.Dense(6, activation='softmax')) #Dense: 全连接层。activation: 激励函数,‘linear’一般用在回归任务的输出层,而‘softmax’一般用在分类任务的输出层
          conv_base.trainable=False
          model.compile(
          loss='categorical_crossentropy',#loss: 拟合损失方法,这里用到了多分类损失函数交叉熵  
          optimizer=Adam(lr=lr),#optimizer: 优化器,梯度下降的优化方法 #rmsprop
          metrics=['accuracy'])
          model.summary() #每个层中的输出形状和参数。
          early_stoping =tf.keras.callbacks.EarlyStopping(monitor="val_loss",min_delta=0,patience=5,verbose=0,baseline=None,restore_best_weights=True)
          history = model.fit(
          train_data, train_label,
          batch_size=16, #更新梯度的批数据的大小 iteration = epochs / batch_size,
          epochs=30,  # 迭代次数
          validation_data=(valadation_data, valadation_label),  # 验证集
          callbacks=[early_stoping])
          return model,history
    model,history = train_classifier(train_data,train_label,valadation_data,valadation_label,)
    

在这里插入图片描述

2.7 模型训练效果

def plot_history(history):
      history_df = pd.DataFrame(history.history)
      history_df[['loss', 'val_loss']].plot()
      plt.title('Train and valadation loss')
      history_df = pd.DataFrame(history.history)
      history_df[['accuracy', 'val_accuracy']].plot()
      plt.title('Train and valadation accuracy')

plot_history(history)

在这里插入图片描述

2.8 模型性能评估

  • 使用测试集进行评估

  • 输出分类报告和混淆矩阵

  • 绘制ROC和AUC曲线

    from sklearn.metrics import classification_report
    from sklearn.metrics import confusion_matrix
    from sklearn.metrics import accuracy_score
    import seaborn as sns
    Y_pred_tta=model.predict_classes(test_data) #模型对测试集数据进行预测
    Y_test = [np.argmax(one_hot)for one_hot in test_label]# 由one-hot转换为普通np数组
    Y_pred_tta=model.predict_classes(test_data) #模型对测试集进行预测
    Y_test = [np.argmax(one_hot)for one_hot in test_label]# 由one-hot转换为普通np数组
    print('验证集分类报告:\n',classification_report(Y_test,Y_pred_tta))
    confusion_mc = confusion_matrix(Y_test,Y_pred_tta)#混淆矩阵
    df_cm = pd.DataFrame(confusion_mc)
    plt.figure(figsize = (10,7))
    sns.heatmap(df_cm, annot=True, cmap="BuPu",linewidths=1.0,fmt="d")
    plt.title('PipeLine accuracy:{0:.3f}'.format(accuracy_score(Y_test,Y_pred_tta)),fontsize=20)
    plt.ylabel('True label',fontsize=20)
    plt.xlabel('Predicted label',fontsize=20)
    

在这里插入图片描述

在这里插入图片描述

from sklearn.metrics import precision_recall_curve
from sklearn.metrics import average_precision_score
from sklearn.metrics import roc_curve
from sklearn import metrics
import matplotlib as mpl

# 计算属于各个类别的概率,返回值的shape = [n_samples, n_classes]
y_score = model.predict_proba(test_data)
# 1、调用函数计算验证集的AUC 
print ('调用函数auc:', metrics.roc_auc_score(test_label, y_score, average='micro'))
# 2、手动计算验证集的AUC
#首先将矩阵test_label和y_score展开,然后计算假正例率FPR和真正例率TPR
fpr, tpr, thresholds = metrics.roc_curve(test_label.ravel(),y_score.ravel())
auc = metrics.auc(fpr, tpr)
print('手动计算auc:', auc)
mpl.rcParams['font.sans-serif'] = u'SimHei'
mpl.rcParams['axes.unicode_minus'] = False
#FPR就是横坐标,TPR就是纵坐标
plt.figure(figsize = (10,7))
plt.plot(fpr, tpr, c = 'r', lw = 2, alpha = 0.7, label = u'AUC=%.3f' % auc)
plt.plot((0, 1), (0, 1), c = '#808080', lw = 1, ls = '--', alpha = 0.7)
plt.xlim((-0.01, 1.02))
plt.ylim((-0.01, 1.02))
plt.xticks(np.arange(0, 1.1, 0.1))
plt.yticks(np.arange(0, 1.1, 0.1))
plt.xlabel('False Positive Rate', fontsize=16)
plt.ylabel('True Positive Rate', fontsize=16)
plt.grid(b=True, ls=':')
plt.legend(loc='lower right', fancybox=True, framealpha=0.8, fontsize=12)
plt.title('37个验证集分类后的ROC和AUC', fontsize=18)
plt.show()

在这里插入图片描述

3 1000种图像分类

这是学长训练的能识别1000种类目标的图像分类模型,演示效果如下

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

4 最后

🧿 更多资料, 项目分享:

https://gitee.com/dancheng-senior/postgraduate

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/924948.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

[JavaWeb]【十三】web后端开发-原理篇

目录 一、SpringBoot配置优先级 1.1 配置优先级比较 1.2 java系统属性和命令行参数 1.3 打包运行jar 1.4 综合优先级​编辑 二、Bean管理 2.1 获取bean 2.2 bean作用域 2.2.1 五种作用域 2.2.2 配置作用域 2.3 第三方bean 2.3.1 编写公共配置类 三、SpringBoot原理 …

二级MySQL(六)——表格数据插入

1、插入完整的数据记录: INSERT INTO tb_student VALUES(2014210103,王玲,女,1998-02-21,安徽,汉,CS1401); 结果: 2、插入指定位置的数据: 直接输入是错的: 需要指出插入的列名称: 结果: 中间两列允许输入…

cvc-complex-type.2.4.a: 发现了以元素 ‘base-extension‘ 开头的无效内容。应以 ‘{layoutlib}‘ 等等开头

不与世俗为伍。哪怕这是自己许给自己的诅咒。 —— 宫崎骏 《红猪》 最近,在使用最新版的AndroidStudio打开一个两年前的项目时候,报了一个如下的错误:【cvc-complex-type.2.4.a: 发现了以元素 ‘base-extension‘ 开头的无效内容】。应以 ‘…

基于PyTorch框架下网络模型的使用与修改

目录 1 损失函数和反向传播1.1 损失函数1.2 反向传播 2 优化器3 现有网络模型的使用及修改4 网络模型的保存与读取4.1 网络模型的保存4.2 网络模型的读取(加载) 5 完整的模型训练套路6 利用GPU训练模型7 完整的模型验证套路: 1 损失函数和反向…

基于DolphinScheduler的调度流程梳理及落地实践

目 录 01 背景‍ 02 主流调度引擎 ‍‍‍‍‍‍‍ 03 DolphinScheduler核心概念及调度过程‍‍‍‍‍‍ 04 开发实践 01‍ 背景‍‍ 随着数据中台概念及相关技术逐渐成熟、落地,不断有企业将其应用到自身业务中,将原本分散的各系统数据进行整合、分析…

【FAQ】安防监控视频汇聚平台EasyCVR接入GB国标设备,无法显示通道信息的排查方法

安防视频监控/视频集中存储/云存储/磁盘阵列EasyCVR平台可拓展性强、视频能力灵活、部署轻快,可支持的主流标准协议有国标GB28181、RTSP/Onvif、RTMP等,以及支持厂家私有协议与SDK接入,包括海康Ehome、海大宇等设备的SDK等。平台既具备传统安…

http协议与apache

http概念: 互联网:是网络的网络,是所有类型网络的母集 因特网:世界上最大的互联网网络。即因特网概念从属于互联网概念 万维网:万维网并非某种特殊的计算机网络,是一个大规模的、联机式的信息贮藏库&…

【前端从0开始】JavaSript——Date对象

创建Date对象 var dateObjnew Date(); 方法 将日期转为字符串 toLocaleString() toLocaleDateString() toLocaleTimeString()获取年、月、日、小时、分、秒 ○1)getYear() //两位的年(2000年前)或三位的年[1900] 获取两位数的年,从1900年开始计算&…

硬件知识积累 USB 接口 type - A type - B type - C 的介绍与功能说明 (简单介绍)

1. USB 的介绍 1.1 USB 的定义 USB : 通用串行总线(英语: Universal Serial Bus,缩写:USB)是一种串口总线标准,也是一种输入输出接口的技术规范,被广泛地应用于个人电脑和移动设备等信息通讯产品,并扩展至摄影器材、数字电视&a…

第四节 C++ 选择结构

文章目录 前言介绍1. if 选择结构1.1 概述1.2. 单 if 语句执行1.2.1 分号和中括号注意事项1.2.2 案例:判断天气 1.3. if - else 语句结构1.3.1 案例1:考试成绩1.3.2 案例2:判断闰年1.3.3 案例3:判断三角形 1.4. 多分支结构1.4.1 语…

VIT Swin Transformer

VIT:https://blog.csdn.net/qq_37541097/article/details/118242600 Swin Transform:https://blog.csdn.net/qq_37541097/article/details/121119988 一、VIT 模型由三个模块组成: Linear Projection of Flattened Patches(Embedding层) Tran…

linux服务TCP参数配置

Linux TCP参数配置 阿里云规范 1.【推荐】高并发服务器建议调小 TCP 协议的 time_wait 超时时间。 说明:操作系统默认 240 秒后,才会关闭处于 time_wait 状态的连接,在高并发访问下,服务器端会因为处于 time_wait 的连接数太多&am…

创邻科技张晨:图数据库,激活数据要素的新基建

“数据经济时代,数据要素产业链的各细分领域均蕴含机遇,图技术作为网络协同和数据智能的底层发动机,将深度掘金数字中国价值潜能”。 8月22日,在2023中国(南京)国际软件产品和信息服务交易博览会的信息技术…

构建 NodeJS 影院预订微服务并使用 docker 部署(04/4)

一、说明 构建一个微服务的电影网站,需要Docker、NodeJS、MongoDB,这样的案例您见过吗?如果对此有兴趣,您就继续往下看吧。 我们前几章的快速回顾 第一篇文章介绍了微服务架构模式,并讨论了使用微服务的优缺点。第二篇…

L1-033 出生年 测试点全过

题目 以上是新浪微博中一奇葩贴:“我出生于1988年,直到25岁才遇到4个数字都不相同的年份。”也就是说,直到2013年才达到“4个数字都不相同”的要求。本题请你根据要求,自动填充“我出生于y年,直到x岁才遇到n个数字都不…

汽车制造业外发文件时 如何阻断泄密风险?

汽车制造业是我国国民经济发展的支柱产业之一,具有产业链长、关联度高、就业面广、消费拉动大等特性。汽车制造行业景气度与宏观经济、居民收入水平和固定资产投资密切相关。 汽车制造业产业链长,关联度高,汽车制造上游行业主要为钢铁、化工…

VScode中写Verilog时,iverilog语法自动纠错功能不起作用

VScode中编写Verilog时,iverilog语法自动纠错功能不起作用 问题:按照教程搭建vscode下Verilog编译环境,发现语法纠错功能一直无效,检查了扩展Verilog-HDL/SystemVerilog/Bluespec SystemVerilog的配置也没有任何问题。 错误原因&a…

【前端从0开始】JavaSript——Array对象

Array对象 导语:页面中的数据,都是从数据库读取出来的,如果返回的数据多,一般情况下会以数组或者对象的形式来进行返回,如果想要删除或者添加数据,就可以使用数组中的方法 如图所示,我们可以通…

RE:从零开始的车载Android HMI(四) - 收音机刻度尺

最近比较忙,研究复杂的东西需要大量集中的时间,但是又抽不出来,就写点简单的东西吧。车载应用开发中有一个几乎避不开的自定义View,就是收音机的刻度条。本篇文章我们来研究如何绘制一个收音机的刻度尺。 本系列文章的目的是在讲…

单核cpu是怎么处理多线程的

首先,要先了解几个概念: 1、线程是CPU调度和分配的基本单位。 2、进程是操作系统进行资源分配(包括cpu、内存、磁盘IO等)的最小单位 。 3、一个进程可以包括多个线程。 4、CPU的时间片是由计算机的操作系统OS里的调度器分配的. …