LeNet-5简介及matlab实现

文章目录

  • 一、LeNet-5网络结构简介
  • 二、LeNet-5每一层的实现原理
    • 2.1. 第一层 (C1) :卷积层(Convolution Layer)
    • 2.2. 第二层 (S2) :池化层(Pooling Layer)
    • 2.3. 第三层(C3):卷积层(Convolution Layer)
    • 2.4. 第四层(S4):池化层(Pooling Layer)
    • 2.5. 第五层(C5):卷积层(全连接卷积层)
    • 2.6. 第六层(F6):全连接层(Fully Connected Layer)
    • 2.7. 第七层(Output):全连接输出层(Softmax分类层)
  • 三、matlab实现LeNet-5
  • 四、训练测试网络

LeNet-5是一种经典的卷积神经网络(CNN),由Yann LeCun等人提出,最初用于手写数字识别任务。它的结构简单清晰,为CNN的发展奠定了基础。

一、LeNet-5网络结构简介

LeNet-5的网络结构如下图所示

在这里插入图片描述

详细参数:

层名类型输入尺寸尺寸输出尺寸激活函数
输入图片28×28×1-32×32×1
C1卷积28×28×1,padding为25×5, 6个卷积核,步长为128×28×6relu
S2池化28×28×62×2 池化,步长为214×14×6
C3卷积14×14×6,padding为05×5, 16个卷积核10×10×16relu
S4池化10×10×162×2 池化,步长为25×5×16
C5卷积(全连接卷积)5×5×165×5, 120个卷积核120×1relu
F6全连接层120全连接84×1relu
输出全连接层84全连接10 (数字类别)softmax

二、LeNet-5每一层的实现原理

2.1. 第一层 (C1) :卷积层(Convolution Layer)

输入: 一张灰度图像,尺寸为 28 × 28 × 1 28\times28\times1 28×28×1

参数:

  • 卷积核尺寸为 5 × 5 5\times5 5×5,共 6个卷积核
  • 偏置项 (bias):每个卷积核对应一个独立的偏置值,因此共有6个偏置值。

输出: 经过卷积后的特征图,共6个,尺寸为 28 × 28 × 6 28\times28\times6 28×28×6

(1)卷积计算原理:

卷积层本质上是将卷积核(滤波器)与输入图像进行卷积操作:
Output ( x , y ) = f ( ∑ i = 1 5 ∑ j = 1 5 Kernel ( i , j ) × Input ( x + i , y + j ) + b ) \text{Output}(x,y) = f\left(\sum_{i=1}^{5}\sum_{j=1}^{5}\text{Kernel}(i,j)\times\text{Input}(x+i,y+j)+b\right) Output(x,y)=f(i=15j=15Kernel(i,j)×Input(x+i,y+j)+b)

  • 这里:
    • Kernel ( i , j ) \text{Kernel}(i,j) Kernel(i,j):表示卷积核的第 i i i行、第 j j j列元素的数值。
    • Input ( x + i , y + j ) \text{Input}(x+i,y+j) Input(x+i,y+j):表示输入图像中对应位置上的数值。
    • b b b:表示该卷积核的偏置项(bias)。
    • f ( ⋅ ) f(\cdot) f():激活函数(例如sigmoid或tanh函数或relu函数),推荐使用relu函数。

上面公式中求和部分的计算原理可以通过下面简单的例子理解

在这里插入图片描述

(2)输出特征图尺寸的计算:

卷积后输出尺寸计算公式为:
Output Size = ( Input Size − Kernel Size ) + 2 × Padding Size Stride + 1 \text{Output Size} = \frac{(\text{Input Size}-\text{Kernel Size})+2\times\text{Padding Size}}{\text{Stride}} + 1 Output Size=Stride(Input SizeKernel Size)+2×Padding Size+1

  • 输入:28×28,卷积核:5×5,Stride(步长)=1,padding=2时,计算结果为:

( 28 − 5 ) + 2 × 2 1 + 1 = 28 \frac{(28 - 5)+2\times2}{1} + 1 = 28 1(285)+2×2+1=28

  • 因此,输出特征图为28×28,6个卷积核则输出为28×28×6。

对于padding的理解,可以通过下面简单的例子理解

当padding为0时

在这里插入图片描述

当padding为2时

在这里插入图片描述

2.2. 第二层 (S2) :池化层(Pooling Layer)

输入: C1层输出特征图,共6个,尺寸为 28 × 28 × 6 28\times28\times6 28×28×6

参数:

  • 池化(Pooling)窗口大小: 2 × 2 2\times2 2×2,步长(Stride)= 2。
  • 无需额外参数,无权值,通常采用平均池化或最大池化,推荐使用最大池化。

输出: 池化后的特征图,共6个,尺寸为 14 × 14 × 6 14\times14\times6 14×14×6

(1)池化计算原理:

池化层的作用是降低特征图的尺寸,同时提取特征的重要信息,增强网络的泛化能力。

常见池化方法:

  • 平均池化(Average Pooling): 取池化窗口区域内所有像素值的平均值作为输出。

    例如窗口区域:
    [ 2 4 6 8 ] \begin{bmatrix} 2 & 4\\ 6 & 8 \end{bmatrix} [2648]
    平均池化的结果为:
    2 + 4 + 6 + 8 4 = 5 \frac{2+4+6+8}{4}=5 42+4+6+8=5

  • 最大池化(Max Pooling): 取池化窗口区域内的最大像素值作为输出。

    以上面的区域为例:
    max ⁡ { 2 , 4 , 6 , 8 } = 8 \max\{2,4,6,8\}=8 max{2,4,6,8}=8

LeNet-5原论文中使用的是平均池化

一个图形化的例子如下所示

在这里插入图片描述

(2)输出特征图尺寸的计算:

池化后输出尺寸计算公式为:
Output Size = Input Size − Pooling Size Stride + 1 \text{Output Size} = \frac{\text{Input Size}-\text{Pooling Size}}{\text{Stride}} + 1 Output Size=StrideInput SizePooling Size+1

  • 输入:28×28,池化窗口:2×2,Stride=2时,计算结果为:

28 − 2 2 + 1 = 14 \frac{28-2}{2}+1=14 2282+1=14

  • 所以S2层输出特征图为 14 × 14 × 6 14\times14\times6 14×14×6

2.3. 第三层(C3):卷积层(Convolution Layer)

输入: 第二层(S2)输出,尺寸为 14 × 14 × 6 14 \times 14 \times 6 14×14×6

参数:

  • 卷积核大小为 5 × 5 5\times 5 5×5,共 16个卷积核
  • 偏置(bias):每个卷积核一个偏置,共16个偏置。

这里卷积的计算需要注意的是,输入是多个通道了,这种情况下的计算可以通过下面的图示理解

在这里插入图片描述

一个简单的计算示例如下,这里输入是 4 × 4 × 3 4\times 4\times3 4×4×3,卷积核大小为 3 × 3 3\times3 3×3,但是也要是三通道

在这里插入图片描述

2.4. 第四层(S4):池化层(Pooling Layer)

输入: 第三层(C3)输出,尺寸为 10 × 10 × 16 10\times10\times16 10×10×16

参数:

  • 池化窗口大小: 2 × 2 2\times2 2×2,步长: 2 2 2
  • LeNet-5使用平均池化(Average Pooling),输出特征图尺寸为: 5 × 5 × 16 5\times5\times16 5×5×16

2.5. 第五层(C5):卷积层(全连接卷积层)

输入:第四层(S4)输出特征图,尺寸为 5 × 5 × 16 5\times5\times16 5×5×16

参数

  • 卷积核尺寸: 5 × 5 5\times5 5×5
  • 卷积核数量:120个
  • 偏置数量:120个(每个卷积核对应1个偏置)

由于输入特征图大小为 5 × 5 × 16 5\times5\times 16 5×5×16,而卷积核也为 5 × 5 5\times5 5×5,因此每个卷积核与输入特征图卷积后会变成 1 × 1 1\times1 1×1 的输出,这相当于对整个特征图做了全连接卷积(即卷积核与整个输入特征图区域进行完全连接)。因此,这一层又称为 全连接卷积层

2.6. 第六层(F6):全连接层(Fully Connected Layer)

输入:第五层(C5)输出,共120个神经元(1维向量)。

参数

  • 全连接层的神经元数量:84个
  • 权重数量: 84 × 120 84\times120 84×120(120个输入与84个神经元全连接)
  • 偏置数量:84个(每个神经元一个偏置)

全连接层的计算本质为矩阵乘法+偏置+激活函数:

  • 计算公式:

Output = f ( W × Input ( 120 × 1 ) + b ) \text{Output} = f\left(W \times \text{Input}_{(120\times1)}+b\right) Output=f(W×Input(120×1)+b)

其中:

  • W W W:是一个大小为 84 × 120 84\times120 84×120 的权重矩阵
  • b b b:大小为 84 × 1 84\times1 84×1 偏置向量
  • f f f:激活函数(如tanh或sigmoid)
  • 输出为84维的向量,即大小为: 84 × 1 84\times1 84×1

2.7. 第七层(Output):全连接输出层(Softmax分类层)

输入:第六层(F6)输出的84个神经元(向量)。

参数

  • 输出类别:10个类别(0-9手写数字)
  • 权重数量: 10 × 84 10\times84 10×84(84个输入与10个输出神经元全连接)
  • 偏置数量:10个(每个输出神经元对应1个偏置)

最后一层通常是全连接层,并使用softmax函数作为分类器:

  • 计算公式:

Z j = ∑ i = 1 84 w j , i x i + b j , j = 1 , 2 , . . . , 10 Z_j = \sum_{i=1}^{84}w_{j,i}x_i + b_j,\quad j=1,2,...,10 Zj=i=184wj,ixi+bj,j=1,2,...,10

其中:

  • Z j Z_j Zj:第 j j j个类别的线性输出值
  • w j , i w_{j,i} wj,i:第 j j j个输出神经元与第 i i i个输入神经元的权重
  • b j b_j bj:第 j j j个输出神经元的偏置

计算Softmax概率:
y j = e Z j ∑ k = 1 10 e Z k y_j = \frac{e^{Z_j}}{\sum_{k=1}^{10}e^{Z_k}} yj=k=110eZkeZj

  • y j y_j yj:为第 j j j 类别的概率值,所有 y j y_j yj 和为1。
  • 最终预测类别即为概率最大的类别。
  • 输出尺寸为: 10 × 1 10\times1 10×1,表示10个类别的概率分布。

分析完每一层的原理后,我们就可以计算一下这个网络的可学习参量了

第一层:卷积核尺寸为 5 × 5 5\times5 5×5,共 6个卷积核,考虑到一个卷积核对应一个偏置量,所以
5 × 5 × 6 + 6 = 156 5\times5\times6+6=156 5×5×6+6=156
第二层:池化层无需要学习参量

第三层:卷积核大小为 5 × 5 5\times 5 5×5,共 16个卷积核,因为这一层的输入是6个通道,并考虑到偏置量,所以
5 × 5 × 6 × 16 + 16 = 2416 5\times5\times6\times16+16=2416 5×5×6×16+16=2416
第四层:池化层无需要学习参量

第五层:卷积核大小为 5 × 5 5\times 5 5×5,共 120个卷积核,因为这一层的输入是16个通道,并考虑到偏置量,所以
5 × 5 × 16 × 120 + 120 = 48120 5\times5\times16\times120+120=48120 5×5×16×120+120=48120
第六层:学习参数为权重数量加偏置,所以
84 × 120 + 84 = 10164 84\times120+84=10164 84×120+84=10164
第七层:学习参数为权重数量加偏置,所以
10 × 84 + 10 = 850 10\times84+10=850 10×84+10=850
所以,这个网络的总学习参数为
156 + 2416 + 48120 + 10164 + 850 = 61706 156+2416+48120+10164+850=61706 156+2416+48120+10164+850=61706

三、matlab实现LeNet-5

这里,我们需要借用到matlab工具栏里APPS里的Deep Network Designer,如下图所示

在这里插入图片描述

在Deep Network Designer, 我们创建一个空白Designer画布

在这里插入图片描述

然后我们可以拖动相应的层到Designer里,并连接各个层,如下图所示

在这里插入图片描述

然后,我们需要设置各个层的参量,对于输入图像来说

在这里插入图片描述

第一层:

在这里插入图片描述

第二层:注意到第一层和二层之间有一个Batchnormalization和激活函数,Batchnormalization一般是为了让训练效果更好,所有的卷积层和全连接层后一般都跟激活函数
在这里插入图片描述

第三层:

在这里插入图片描述

第四层:

在这里插入图片描述

第五层:

在这里插入图片描述

第六层:

在这里插入图片描述

第七层:

![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/4b903413d16047218c7c0ea6df617a14.png#pic_center -=400x)

设置完成后,我们就可以用Analyze这个按钮分析这个网络了,分析内容很详细,可以看到这个网络的可学习参量为61.7k,跟我们上面计算的结果相同。至此,我们就完成了LeNet-5的搭建。

在这里插入图片描述

然后用Export按钮输出到工作区,这个网络的名称会自动命名为net_1。

在这里插入图片描述

四、训练测试网络

加载图像数据集

dataFolder = "DigitsData";  % 指定图像数据所在的文件夹路径
imds = imageDatastore(dataFolder, ...IncludeSubfolders=true, ...        % 包括子文件夹中的图像LabelSource="foldernames");        % 使用文件夹名称作为图像的标签

imageDatastore 用于批量加载图像,并自动将图像按文件夹名称分类(用于监督学习)。


在这里插入图片描述

可视化部分图像

figure
tiledlayout("flow");                  % 设置自适应布局以显示多个图像
perm = randperm(10000, 20);          % 从 10000 张图像中随机选取 20 张
for i = 1:20nexttile                         % 在下一图块中显示图像imshow(imds.Files{perm(i)});    % 显示图像文件路径对应的图像
end

随机选出 20 张图像用于展示,验证数据是否正确读取和标注。


在这里插入图片描述

查看类别和样本数量

classNames = categories(imds.Labels);     % 提取所有类别名称
labelCount = countEachLabel(imds);        % 统计每个类别的图像数量

有助于检查数据是否均衡,每类是否数量相近。


查看图像尺寸

matlab复制编辑img = readimage(imds,1);     % 读取第 1 张图像
size(img)                  % 查看图像尺寸(应该为 28×28×1)

确保图像大小和通道数(灰度或彩色)与网络输入一致。


划分训练集、验证集、测试集

[imdsTrain, imdsValidation, imdsTest] = splitEachLabel(imds, 0.7, 0.15, 0.15, "randomized");

从每个类别中随机划分出 70% 用于训练,15% 用于验证,15% 用于测试。


设置训练选项

options = trainingOptions("sgdm", ...InitialLearnRate=0.01, ...             % 初始学习率MaxEpochs=4, ...                       % 最大训练轮数Shuffle="every-epoch", ...             % 每个 epoch 打乱训练数据ValidationData=imdsValidation, ...     % 指定验证数据集ValidationFrequency=30, ...            % 每训练 30 个 mini-batch 进行一次验证Plots="training-progress", ...         % 实时显示训练过程图表Metrics="accuracy", ...                % 关注准确率指标Verbose=false);                        % 不在命令行输出详细训练信息

控制训练过程的关键参数,适用于小型数据集的快速实验。


训练神经网络

net = trainnet(imdsTrain, net_1, "crossentropy", options);

使用自定义网络 net_1 和交叉熵损失函数对训练集进行训练,返回训练好的网络 net


在这里插入图片描述

在测试集上评估准确率

accuracy = testnet(net, imdsTest, "accuracy");

在未见过的测试集上评估模型性能,输出预测准确率(值范围 0~1)。


进行预测并生成标签

scores = minibatchpredict(net, imdsTest);               % 对测试集进行批量预测,输出每类得分
YTest = scores2label(scores, classNames);               % 将得分转换为预测的标签

scores 是每张图像对每个类别的得分;scores2label 会选择得分最高的类别作为预测结果。


可视化预测结果

numTestObservations = numel(imdsTest.Files);        % 测试集中图像的总数
idx = randi(numTestObservations, 9, 1);             % 随机选取 9 个图像索引用于展示figure
tiledlayout("flow")                                 % 设置图像自动排列布局
for i = 1:9nexttileimg = readimage(imdsTest, idx(i));              % 读取图像imshow(img)                                     % 显示图像title("Predicted Class: " + string(YTest(idx(i))))  % 显示预测类别
end

随机从测试集中挑选 9 张图像,并在图像上标注预测的类别结果,可用于人工评估模型表现。

在这里插入图片描述

完整代码如下

%%
dataFolder = "DigitsData";  % 指定图像数据所在的文件夹路径
imds = imageDatastore(dataFolder, ...IncludeSubfolders=true, ...        % 包括子文件夹中的图像LabelSource="foldernames");        % 使用文件夹名称作为图像的标签figure
tiledlayout("flow");                  % 设置自适应布局以显示多个图像
perm = randperm(10000, 20);          % 从 10000 张图像中随机选取 20 张
for i = 1:20nexttile                         % 在下一图块中显示图像imshow(imds.Files{perm(i)});    % 显示图像文件路径对应的图像
end
%%
classNames = categories(imds.Labels);     % 提取所有类别名称
labelCount = countEachLabel(imds);        % 统计每个类别的图像数量%%
img = readimage(imds,1);     % 读取第 1 张图像
size(img);                   % 查看图像尺寸(应该为 28×28×1)%%
% 从每个类别中随机划分出 70% 用于训练,15% 用于验证,15% 用于测试。
[imdsTrain, imdsValidation, imdsTest] = splitEachLabel(imds, 0.7, 0.15, 0.15, "randomized");%%
% options = trainingOptions("sgdm", ...
%     InitialLearnRate=0.01, ...
%     MaxEpochs=4, ...
%     Shuffle="every-epoch", ...
%     ValidationData=imdsValidation, ...
%     ValidationFrequency=30, ...
%     Plots="training-progress", ...
%     Metrics="accuracy", ...
%     Verbose=false);
options = trainingOptions("sgdm", ...InitialLearnRate=0.01, ...             % 初始学习率MaxEpochs=4, ...                       % 最大训练轮数Shuffle="every-epoch", ...             % 每个 epoch 打乱训练数据ValidationData=imdsValidation, ...     % 指定验证数据集ValidationFrequency=30, ...            % 每训练 30 个 mini-batch 进行一次验证Plots="training-progress", ...         % 实时显示训练过程图表Metrics="accuracy", ...                % 关注准确率指标Verbose=false);                        % 不在命令行输出详细训练信息%%
% 使用自定义网络 net_1 和交叉熵损失函数对训练集进行训练,返回训练好的网络 net。
net = trainnet(imdsTrain,net_1,"crossentropy",options);% 在未见过的测试集上评估模型性能,输出预测准确率(值范围 0~1)。
accuracy = testnet(net, imdsTest, "accuracy");scores = minibatchpredict(net, imdsTest);               % 对测试集进行批量预测,输出每类得分
YTest = scores2label(scores, classNames);               % 将得分转换为预测的标签numTestObservations = numel(imdsTest.Files);        % 测试集中图像的总数
idx = randi(numTestObservations, 9, 1);             % 随机选取 9 个图像索引用于展示figure
tiledlayout("flow")                                 % 设置图像自动排列布局
for i = 1:9nexttileimg = readimage(imdsTest, idx(i));              % 读取图像imshow(img)                                     % 显示图像title("Predicted Class: " + string(YTest(idx(i))))  % 显示预测类别
end

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

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

相关文章

【LLM】MCP(Python):实现 stdio 通信的Client与Server

本文将详细介绍如何使用 Model Context Protocol (MCP) 在 Python 中实现基于 STDIO 通信的 Client 与 Server。MCP 是一个开放协议,它使 LLM 应用与外部数据源和工具之间的无缝集成成为可能。无论你是构建 AI 驱动的 IDE、改善 chat 交互,还是构建自定义…

Docker 安装 Elasticsearch 教程

目录 一、安装 Elasticsearch 二、安装 Kibana 三、安装 IK 分词器 四、Elasticsearch 常用配置 五、Elasticsearch 常用命令 一、安装 Elasticsearch (一)创建 Docker 网络 因为后续还需要部署 Kibana 容器,所以需要让 Elasticsearch…

Swagger @ApiOperation

ApiOperation 注解并非 Spring Boot 自带的注解,而是来自 Swagger 框架,Swagger 是一个规范且完整的框架,用于生成、描述、调用和可视化 RESTful 风格的 Web 服务,而 ApiOperation 主要用于为 API 接口的操作添加描述信息。以下为…

【奇点时刻】GPT4o新图像生成模型底层原理深度洞察报告(篇2)

由于上一篇解析深度不足,经过查看学习相关论文,以下是一份对 GPT-4o 最新的图像生成模型 的深度梳理与洞察,从模型原理到社区解读、对比传统扩散模型,再到对未来趋势的分析。为了便于阅读,整理成以下七个部分&#xff…

C# 窗体应用(.FET Framework ) 打开文件操作

一、 打开文件或文件夹加载数据 1. 定义一个列表用来接收路径 public List<string> paths new List<string>();2. 打开文件选择一个文件并将文件放入列表中 OpenFileDialog open new OpenFileDialog(); // 过滤 open.Filter "(*.jpg;*.jpge;*.bmp;*.png…

Scala 面向对象编程总结

​​​抽象属性和抽象方法 基本语法 定义抽象类&#xff1a;abstract class Person{} //通过 abstract 关键字标记抽象类定义抽象属性&#xff1a;val|var name:String //一个属性没有初始化&#xff0c;就是抽象属性定义抽象方法&#xff1a;def hello():String //只声明而没…

人工智能赋能工业制造:智能制造的未来之路

一、引言 随着人工智能技术的飞速发展&#xff0c;其应用场景不断拓展&#xff0c;从消费电子到医疗健康&#xff0c;从金融科技到交通运输&#xff0c;几乎涵盖了所有行业。而工业制造作为国民经济的支柱产业&#xff0c;也在人工智能的浪潮中迎来了深刻的变革。智能制造&…

元宇宙概念下,UI 设计如何打造沉浸式体验?

一、元宇宙时代UI设计的核心趋势 在元宇宙概念下&#xff0c;UI设计的核心目标是打造沉浸式体验&#xff0c;让用户在虚拟世界中感受到身临其境的交互效果。以下是元宇宙时代UI设计的几个核心趋势&#xff1a; 沉浸式体验设计 元宇宙的核心是提供沉浸式体验&#xff0c;UI设计…

AI 如何帮助我们提升自己,不被替代

在当今快速发展的时代&#xff0c;人工智能&#xff08;AI&#xff09;正逐渐渗透到生活的方方面面。许多人担心 AI 会取代人类的工作&#xff0c;然而&#xff0c;AI 更多的是作为一种强大的赋能工具&#xff0c;帮助我们提升自身能力&#xff0c;让我们在工作中更具竞争力。以…

基于SpringBoot+Vue实现的二手交易市场平台功能一

一、前言介绍&#xff1a; 1.1 项目摘要 随着社会的发展和人们生活水平的提高&#xff0c;消费者购买能力的提升导致产生了大量的闲置物品&#xff0c;这些闲置物品具有一定的经济价值。特别是在高校环境中&#xff0c;学生群体作为一个具有一定消费水平的群体&#xff0c;每…

k8s安装cri驱动创建storageclass动态类

部署nfs服务器 #所有k8s节点安装nfs客户端 yum install -y nfs-utils mkdir -p /nfs/share echo "/nfs/share *(rw,sync,no_root_squash)" >> /etc/exports systemctl enable --now nfs-serverhelm部署nfs的provisioner&sc 所有k8s节点安装客户端 yu…

SpringBoot + Netty + Vue + WebSocket实现在线聊天

最近想学学WebSocket做一个实时通讯的练手项目 主要用到的技术栈是WebSocket Netty Vue Pinia MySQL SpringBoot&#xff0c;实现一个持久化数据&#xff0c;单一群聊&#xff0c;支持多用户的聊天界面 下面是实现的过程 后端 SpringBoot启动的时候会占用一个端口&#xff…

大数据Spark(五十七):Spark运行架构与MapReduce区别

文章目录 Spark运行架构与MapReduce区别 一、Spark运行架构 二、Spark与MapReduce区别 Spark运行架构与MapReduce区别 一、Spark运行架构 Master:Spark集群中资源管理主节点&#xff0c;负责管理Worker节点。Worker:Spark集群中资源管理的从节点&#xff0c;负责任务的运行…

【爬虫】网页抓包工具--Fiddler

网页抓包工具对比&#xff1a;Fiddler与Sniff Master Fiddler基础知识 Fiddler是一款强大的抓包工具&#xff0c;它的工作原理是作为web代理服务器运行&#xff0c;默认代理地址是127.0.0.1&#xff0c;端口8888。代理服务器位于客户端和服务器之间&#xff0c;拦截所有HTTP/…

Redis:集群

为什么要有集群&#xff1f; Redis 集群&#xff08;Redis Cluster&#xff09;是 Redis 官方提供的分布式解决方案&#xff0c;用于解决单机 Redis 在数据容量、并发处理能力和高可用性上的局限。通过 Redis 集群&#xff0c;可以实现数据分片、故障转移和高可用性&#xff0…

【2012】【论文笔记】太赫兹波在非磁化等离子体——

前言 类型 太赫兹 + 等离子体 太赫兹 + 等离子体 太赫兹+等离子体 期刊 物理学报 物理学报 物理学报 作者

Linux字符驱动设备开发入门之框架搭建

声明 本博客所记录的关于正点原子i.MX6ULL开发板的学习笔记&#xff0c;&#xff08;内容参照正点原子I.MX6U嵌入式linux驱动开发指南&#xff0c;可在正点原子官方获取正点原子Linux开发板 — 正点原子资料下载中心 1.0.0 文档&#xff09;&#xff0c;旨在如实记录我在学校学…

小刚说C语言刷题——第15讲 多分支结构

1.多分支结构 所谓多分支结构是指在选择的时候有多种选择。根据条件满足哪个分支&#xff0c;就走对应分支的语句。 2.语法格式 if(条件1) 语句1; else if(条件2) 语句2; else if(条件3) 语句3; ....... else 语句n; 3.示例代码 从键盘输入三条边的长度&#xff0c;…

Apache httpclient okhttp(1)

学习链接 Apache httpclient & okhttp&#xff08;1&#xff09; Apache httpclient & okhttp&#xff08;2&#xff09; httpcomponents-client github apache httpclient文档 apache httpclient文档详细使用 log4j日志官方文档 【Java基础】- HttpURLConnection…

洛谷题单3-P1420 最长连号-python-流程图重构

题目描述 输入长度为 n n n 的一个正整数序列&#xff0c;要求输出序列中最长连号的长度。 连号指在序列中&#xff0c;从小到大的连续自然数。 输入格式 第一行&#xff0c;一个整数 n n n。 第二行&#xff0c; n n n 个整数 a i a_i ai​&#xff0c;之间用空格隔开…