P19:Inception v1算法实战与解析
- 🍨 本文为🔗365天深度学习训练营 中的学习记录博客
- 🍖 原作者:K同学啊
一、模型结构
Inception V1 的主要特点是在一个网络中同时使用不同大小的卷积核(1x1、3x3、5x5)和池化操作来提取多尺度特征。以下是 Inception V1 的主要结构:
-
卷积和池化层
- 模型开始部分使用常规的卷积层和池化层对输入图像进行特征提取和降维。
- 示例代码中,
conv1
和maxpool1
组合用于初步特征提取和下采样。
-
Inception 模块
- Inception 模块是 Inception V1 的核心,每个模块包含四个分支:
- 1x1 卷积分支:用于降低通道数,减少计算量,同时提取低级特征。
- 1x1 卷积 + 3x3 卷积分支:先降低通道数,再使用 3x3 卷积提取中等尺度特征。
- 1x1 卷积 + 5x5 卷积分支:用于提取更大尺度的特征,5x5 卷积前的 1x1 卷积用于降维以减少计算量。
- 3x3 最大池化 + 1x1 卷积分支:池化用于特征压缩,随后 1x1 卷积调整通道数。
- Inception 模块是 Inception V1 的核心,每个模块包含四个分支:
-
辅助分类器
- Inception V1 引入了两个辅助分类器(
InceptionAux
),它们连接在后面的 Inception 模块中。 - 辅助分类器的作用是:
- 在训练过程中提供额外的梯度信号,帮助缓解梯度消失问题。
- 对中间层的特征进行分类,促使网络在不同层次学习到有用的特征。
- Inception V1 引入了两个辅助分类器(
-
全局平均池化和全连接层
- 网络最后使用全局平均池化(
AdaptiveAvgPool2d
)将特征图转化为固定大小的特征向量。 - 随后通过全连接层(
fc
)进行最终的分类。
- 网络最后使用全局平均池化(
训练过程
在训练过程中,模型会同时计算主分类器和辅助分类器的损失,并将它们加权求和作为总损失。这种设计有助于网络更快地收敛。
模型优势
- 多尺度特征提取:Inception 模块通过不同大小的卷积核同时捕捉多种尺度的特征,提高模型的特征表达能力。
- 计算效率:1x1 卷积用于降维,有效减少计算量和参数数量。
- 梯度流动改善:辅助分类器帮助缓解梯度消失问题,使深层网络更容易训练。
程序结构图
卷积层并行结构
Inception V1 的卷积层并行结构是其核心创新之一。这种结构在一个层中并行使用多个不同大小的卷积核(1×1、3×3、5×5)以及池化操作,目的是同时提取不同尺度的特征。具体来说:
- 多尺度特征提取:不同大小的卷积核可以捕捉到图像的不同尺度特征。小卷积核(如 1×1)适合捕捉精细的局部特征,而大卷积核(如 5×5)适合捕捉更广泛的上下文信息。
- 并行分支:每个分支独立进行卷积操作,然后将所有分支的输出在通道维度上进行拼接,形成最终的输出特征图。这种设计使得网络能够在同一层中处理多种尺度的信息。
这种并行结构的优点包括:
- 丰富的特征表达:通过多尺度特征提取,网络能够更好地理解和表示图像内容。
- 灵活的特征组合:不同分支的特征可以相互补充,提高模型的表达能力。
1×1 的卷积块
1×1 卷积块在 Inception V1 中起着至关重要的作用,主要有两个用途:
-
降维:
- 在 3×3 或 5×5 卷积之前使用 1×1 卷积可以减少输入的通道数,从而降低计算量。
- 例如,如果输入通道数为 192,通过 1×1 卷积将其降至 96,然后再进行 3×3 卷积,这样可以减少参数数量和计算量。
-
特征变换:
- 1×1 卷积可以看作是一种特征变换操作,它可以在不改变空间尺寸的情况下,对特征进行线性组合和非线性变换。
- 这种变换有助于提取更高级的特征表示。
具体来说,1×1 卷积的操作可以表示为:
y i , j , k = σ ( ∑ m = 0 C − 1 w k , m ⋅ x i , j , m + b k ) y_{i,j,k} = \sigma\left( \sum_{m=0}^{C-1} w_{k,m} \cdot x_{i,j,m} + b_k \right) yi,j,k=σ(m=0∑C−1wk,m⋅xi,j,m+bk)
其中:
- (x_{i,j,m}) 是输入特征图在位置 ((i,j)) 的第 (m) 个通道的值。
- (w_{k,m}) 是第 (k) 个 1×1 卷积核在第 (m) 个输入通道的权重。
- (b_k) 是偏置项。
- (\sigma) 是激活函数,如 ReLU。
1×1 卷积的优点包括:
- 减少参数量:通过降维,显著减少后续卷积层的参数数量。
- 增加非线性:结合激活函数,增加网络的非线性表达能力。
- 加速计算:降低计算复杂度,提高网络的运行效率。
这种卷积块在 Inception V1 的每个模块中都被广泛应用,是实现模型高效性和有效性的关键组件之一。
卷积块计算量对比
如下是相同的卷积结果但是不同的卷积方式,下面将计算一下计算量,观察为何能通过小卷积核升维减少计算量
好的,我将详细列出每一步的结果。
第一种:直接使用5×5卷积核的计算过程
输入特征图大小:100×100×128
卷积核大小:5×5×128
卷积核数量:256
填充大小:2
步幅:1
-
填充后的输入大小:
- 填充后输入特征图大小为 104×104×128
-
卷积操作:
- 将每个 5×5×128 的卷积核与输入特征图进行逐元素相乘并求和,得到一个100×100的特征图,对应一个输出通道。
-
输出特征图大小:
- 输出特征图大小为 (100 ×100 × 256)。
-
参数数量:
- 每个卷积核参数数量为 (5 × 5 × 128 = 3200)。
- 256个卷积核的总参数数量为 (256 ×3200 = 819200)。
第二种:先使用1×1卷积降维,再使用5×5卷积的计算过程
输入特征图大小:100×100×128
1×1卷积核大小:1×1×128
1×1卷积核数量:32
5×5卷积核大小:5×5×32
5×5卷积核数量:256
填充大小(1×1卷积):0
填充大小(5×5卷积):2
步幅:1
-
1×1卷积降维过程:
- 输入特征图大小:(100 × 100 ×128)
- 卷积核大小:(1 ×1 ×128)
- 卷积核数量:32
- 填充大小:0
- 步幅:1
- 输出特征图大小:(100×100×32)
- 参数数量:(1 ×1 ×128 ×32 = 4096)
-
5×5卷积升维过程:
- 输入特征图大小:(100×100 ×32)
- 卷积核大小:(5×5×32)
- 卷积核数量:256
- 填充大小:2
- 步幅:1
- 填充后输入特征图大小:(104×104×32)
- 输出特征图大小:(100×100×256)
- 参数数量:(5 ×5 ×32×256 = 204800)
-
总参数数量:
- 1×1卷积参数数量:4096
- 5×5卷积参数数量:204800
- 总参数数量:(4096 + 204800 = 208896)
两种方式的对比
-
第一种方式:
- 输出特征图大小:(100×100×256)
- 参数数量:819200
-
第二种方式:
- 输出特征图大小:(100 ×100 ×256)
- 参数数量:208896
通过对比可以看出,第二种方式在保持输出特征图大小不变的情况下,参数数量显著减少,计算量也更小,这是由于1×1卷积有效地降低了通道数。
二、 前期准备
1. 导入库
import torch
import torch.nn as nn
import torchvision.transforms as transforms
import torchvision
from torchvision import transforms, datasets
import os,PIL,pathlib
import os,PIL,random,pathlib
import torch.nn.functional as F
from PIL import Image
import matplotlib.pyplot as plt
#隐藏警告
import warnings
2.导入数据
data_dir = './data/4-data/'
data_dir = pathlib.Path(data_dir)
#print(data_dir)
data_paths = list(data_dir.glob('*'))
classeNames = [str(path).split("\\")[2] for path in data_paths]
#print(classeNames)
total_datadir = './data/4-data/'train_transforms = transforms.Compose([transforms.Resize([224, 224]), # 将输入图片resize成统一尺寸transforms.ToTensor(), # 将PIL Image或numpy.ndarray转换为tensor,并归一化到[0,1]之间transforms.Normalize( # 标准化处理-->转换为标准正太分布(高斯分布),使模型更容易收敛mean=[0.485, 0.456, 0.406],std=[0.229, 0.224, 0.225]) # 其中 mean=[0.485,0.456,0.406]与std=[0.229,0.224,0.225] 从数据集中随机抽样计算得到的。
])total_data = datasets.ImageFolder(total_datadir,transform=train_transforms)
3.划分数据集
train_size = int(0.8 * len(total_data))
test_size = len(total_data) - train_size
train_dataset, test_dataset = torch.utils.data.random_split(total_data, [train_size, test_size])
batch_size = 32train_dl = torch.utils.data.DataLoader(train_dataset,batch_size=batch_size,shuffle=True,num_workers=1)
test_dl = torch.utils.data.DataLoader(test_dataset,batch_size=batch_size,shuffle=True,num_workers=1)
三、模型设计
1. 神经网络的搭建
class InceptionV1(nn.Module):def __init__(self, in_channels, ch1x1, ch3x3red, ch3x3, ch5x5red, ch5x5, pool_proj):super(InceptionV1, self).__init__()# 1x1 conv branchself.branch1 = nn.Sequential(nn.Conv2d(in_channels, ch1x1, kernel_size=1),nn.BatchNorm2d(ch1x1),nn.ReLU(inplace=True))# 1x1 conv -> 3x3 conv branchself.branch2 = nn.Sequential(nn.Conv2d(in_channels, ch3x3red, kernel_size=1),nn.BatchNorm2d(ch3x3red),nn.ReLU(inplace=True),nn.Conv2d(ch3x3red, ch3x3, kernel_size=3, padding=1),nn.BatchNorm2d(ch3x3),nn.ReLU(inplace=True))# 1x1 conv -> 5x5 conv branchself.branch3 = nn.Sequential(nn.Conv2d(in_channels, ch5x5red, kernel_size=1),nn.BatchNorm2d(ch5x5red),nn.ReLU(inplace=True),nn.Conv2d(ch5x5red, ch5x5, kernel_size=5, padding=2),nn.BatchNorm2d(ch5x5),nn.ReLU(inplace=True))# 3x3 max pooling -> 1x1 conv branchself.branch4 = nn.Sequential(nn.MaxPool2d(kernel_size=3, stride=1, padding=1),nn.Conv2d(in_channels, pool_proj, kernel_size=1),nn.BatchNorm2d(pool_proj),nn.ReLU(inplace=True))def forward(self, x):branch1 = self.branch1(x)branch2 = self.branch2(x)branch3 = self.branch3(x)branch4 = self.branch4(x)outputs = [branch1, branch2, branch3, branch4]return torch.cat(outputs, 1)# 定义 Inception 辅助分类器
class InceptionAux(nn.Module):def __init__(self, in_channels, num_classes):super(InceptionAux, self).__init__()self.conv = nn.Sequential(nn.Conv2d(in_channels, 128, kernel_size=1),nn.BatchNorm2d(128),nn.ReLU(inplace=True))self.fc = nn.Sequential(nn.Linear(2048, 1024),nn.ReLU(inplace=True),nn.Dropout(0.7),nn.Linear(1024, num_classes))def forward(self, x):x = F.adaptive_avg_pool2d(x, (4, 4))x = self.conv(x)x = torch.flatten(x, 1)x = self.fc(x)return x# 定义完整的 Inception V1 模型
class InceptionV1Model(nn.Module):def __init__(self, num_classes=4):super(InceptionV1Model, self).__init__()self.conv1 = nn.Sequential(nn.Conv2d(3, 64, kernel_size=7, stride=2, padding=3),nn.BatchNorm2d(64),nn.ReLU(inplace=True))self.maxpool1 = nn.MaxPool2d(3, stride=2, padding=1)self.conv2 = nn.Sequential(nn.Conv2d(64, 64, kernel_size=1),nn.BatchNorm2d(64),nn.ReLU(inplace=True),nn.Conv2d(64, 192, kernel_size=3, padding=1),nn.BatchNorm2d(192),nn.ReLU(inplace=True))self.maxpool2 = nn.MaxPool2d(3, stride=2, padding=1)# Inception blocksself.inception3a = InceptionV1(192, 64, 96, 128, 16, 32, 32)self.inception3b = InceptionV1(256, 128, 128, 192, 32, 96, 64)self.maxpool3 = nn.MaxPool2d(3, stride=2, padding=1)self.inception4a = InceptionV1(480, 192, 96, 208, 16, 48, 64)self.inception4b = InceptionV1(512, 160, 112, 224, 24, 64, 64)self.inception4c = InceptionV1(512, 128, 128, 256, 24, 64, 64)self.inception4d = InceptionV1(512, 112, 144, 288, 32, 64, 64)self.inception4e = InceptionV1(528, 256, 160, 320, 32, 128, 128)self.maxpool4 = nn.MaxPool2d(3, stride=2, padding=1)self.inception5a = InceptionV1(832, 256, 160, 320, 32, 128, 128)self.inception5b = InceptionV1(832, 384, 192, 384, 48, 128, 128)# Auxiliary classifiersself.aux1 = InceptionAux(512, num_classes)self.aux2 = InceptionAux(528, num_classes)self.avgpool = nn.AdaptiveAvgPool2d((1, 1))self.dropout = nn.Dropout(0.4)self.fc = nn.Linear(1024, num_classes)def forward(self, x):x = self.conv1(x)x = self.maxpool1(x)x = self.conv2(x)x = self.maxpool2(x)x = self.inception3a(x)x = self.inception3b(x)x = self.maxpool3(x)x = self.inception4a(x)aux1 = self.aux1(x) if self.training else Nonex = self.inception4b(x)x = self.inception4c(x)x = self.inception4d(x)aux2 = self.aux2(x) if self.training else Nonex = self.inception4e(x)x = self.maxpool4(x)x = self.inception5a(x)x = self.inception5b(x)x = self.avgpool(x)x = torch.flatten(x, 1)x = self.dropout(x)x = self.fc(x)if self.training:return x, aux1, aux2else:return x
2.设置损失值等超参数
device = "cuda" if torch.cuda.is_available() else "cpu"# 模型初始化
input_shape = (224, 224, 3)
num_classes = len(classeNames)
model = ResNeXt50(input_shape=input_shape, num_classes=num_classes).to(device)
print(summary(model, (3, 224, 224)))loss_fn = nn.CrossEntropyLoss() # 创建损失函数
learn_rate = 1e-4 # 学习率
opt = torch.optim.SGD(model.parameters(),lr=learn_rate)
epochs = 10
train_loss = []
train_acc = []
test_loss = []
test_acc = []
----------------------------------------------------------------Layer (type) Output Shape Param #
================================================================Conv2d-1 [-1, 64, 112, 112] 9,472BatchNorm2d-2 [-1, 64, 112, 112] 128ReLU-3 [-1, 64, 112, 112] 0MaxPool2d-4 [-1, 64, 56, 56] 0.... .....BatchNorm2d-207 [-1, 128, 7, 7] 256ReLU-208 [-1, 128, 7, 7] 0InceptionV1-209 [-1, 1024, 7, 7] 0
AdaptiveAvgPool2d-210 [-1, 1024, 1, 1] 0Dropout-211 [-1, 1024] 0Linear-212 [-1, 2] 2,050
================================================================
Total params: 10,324,502
Trainable params: 10,324,502
Non-trainable params: 0
----------------------------------------------------------------
Input size (MB): 0.57
Forward/backward pass size (MB): 94.24
Params size (MB): 39.38
Estimated Total Size (MB): 134.20
----------------------------------------------------------------
3. 设置训练函数
def train(dataloader, model, loss_fn, optimizer):size = len(dataloader.dataset)num_batches = len(dataloader)train_loss, train_acc = 0, 0model.train()for X, y in dataloader:X, y = X.to(device), y.to(device)pred = model(X)if isinstance(pred, tuple):loss = loss_fn(pred[0], y) + 0.3 * loss_fn(pred[1], y) + 0.3 * loss_fn(pred[2], y)else:loss = loss_fn(pred, y)optimizer.zero_grad()loss.backward()optimizer.step()train_acc += (pred[0].argmax(1) == y).type(torch.float).sum().item() if isinstance(pred, tuple) else (pred.argmax(1) == y).type(torch.float).sum().item()train_loss += loss.item()train_acc /= sizetrain_loss /= num_batchesreturn train_acc, train_loss
4. 设置测试函数
def test(dataloader, model, loss_fn):size = len(dataloader.dataset)num_batches = len(dataloader)test_loss, test_acc = 0, 0model.eval()with torch.no_grad():for X, y in dataloader:X, y = X.to(device), y.to(device)pred = model(X)if isinstance(pred, tuple):test_loss += (loss_fn(pred[0], y) + 0.3 * loss_fn(pred[1], y) + 0.3 * loss_fn(pred[2], y)).item()test_acc += (pred[0].argmax(1) == y).type(torch.float).sum().item()else:test_loss += loss_fn(pred, y).item()test_acc += (pred.argmax(1) == y).type(torch.float).sum().item()test_acc /= sizetest_loss /= num_batchesreturn test_acc, test_loss
5. 创建导入本地图片预处理模块
def predict_one_image(image_path, model, transform, classes):test_img = Image.open(image_path).convert('RGB')test_img = transform(test_img)img = test_img.to(device).unsqueeze(0)model.eval()output = model(img)_, pred = torch.max(output, 1)pred_class = classes[pred]print(f'预测结果是:{pred_class}')
6. 主函数
if __name__ == '__main__':device = "cuda" if torch.cuda.is_available() else "cpu"# 模型初始化num_classes = len(classeNames)model = InceptionV1Model(num_classes=num_classes).to(device)print(summary(model, (3, 224, 224)))loss_fn = nn.CrossEntropyLoss()learn_rate = 1e-4opt = optim.SGD(model.parameters(), lr=learn_rate)epochs = 10train_loss = []train_acc = []test_loss = []test_acc = []for epoch in range(epochs):model.train()epoch_train_acc, epoch_train_loss = train(train_dl, model, loss_fn, opt)model.eval()epoch_test_acc, epoch_test_loss = test(test_dl, model, loss_fn)train_acc.append(epoch_train_acc)train_loss.append(epoch_train_loss)test_acc.append(epoch_test_acc)test_loss.append(epoch_test_loss)template = ('Epoch:{:2d}, Train_acc:{:.1f}%, Train_loss:{:.3f}, Test_acc:{:.1f}%, Test_loss:{:.3f}')print(template.format(epoch + 1, epoch_train_acc * 100, epoch_train_loss, epoch_test_acc * 100, epoch_test_loss))print('Done')# 绘制训练和测试曲线warnings.filterwarnings("ignore")plt.rcParams['font.sans-serif'] = ['SimHei']plt.rcParams['axes.unicode_minus'] = Falseplt.rcParams['figure.dpi'] = 100epochs_range = range(epochs)plt.figure(figsize=(12, 3))plt.subplot(1, 2, 1)plt.plot(epochs_range, train_acc, label='Training Accuracy')plt.plot(epochs_range, test_acc, label='Test Accuracy')plt.legend(loc='lower right')plt.title('Training and Validation Accuracy')plt.subplot(1, 2, 2)plt.plot(epochs_range, train_loss, label='Training Loss')plt.plot(epochs_range, test_loss, label='Test Loss')plt.legend(loc='upper right')plt.title('Training and Validation Loss')plt.show()classes = list(total_data.class_to_idx.keys())predict_one_image(image_path='./data/4-data/Monkeypox/M01_01_00.jpg',model=model,transform=train_transforms,classes=classes)# 保存模型PATH = './model_inception.pth'torch.save(model.state_dict(), PATH)# 加载模型model.load_state_dict(torch.load(PATH, map_location=device))
结果
Epoch: 1, Train_acc:55.2%, Train_loss:1.118, Test_acc:56.4%, Test_loss:0.688
Epoch: 2, Train_acc:55.5%, Train_loss:1.107, Test_acc:53.4%, Test_loss:0.680
Epoch: 3, Train_acc:55.6%, Train_loss:1.108, Test_acc:55.0%, Test_loss:0.678
Epoch: 4, Train_acc:58.1%, Train_loss:1.101, Test_acc:54.8%, Test_loss:0.678
Epoch: 5, Train_acc:57.9%, Train_loss:1.097, Test_acc:56.2%, Test_loss:0.676
Epoch: 6, Train_acc:59.0%, Train_loss:1.084, Test_acc:57.3%, Test_loss:0.672
Epoch: 7, Train_acc:61.1%, Train_loss:1.083, Test_acc:58.5%, Test_loss:0.665
Epoch: 8, Train_acc:60.2%, Train_loss:1.078, Test_acc:58.3%, Test_loss:0.664
Epoch: 9, Train_acc:60.4%, Train_loss:1.074, Test_acc:59.0%, Test_loss:0.662
Epoch:10, Train_acc:60.7%, Train_loss:1.072, Test_acc:59.7%, Test_loss:0.660
Done
相关文章:
P19:Inception v1算法实战与解析
🍨 本文为🔗365天深度学习训练营 中的学习记录博客🍖 原作者:K同学啊 一、模型结构 Inception V1 的主要特点是在一个网络中同时使用不同大小的卷积核(1x1、3x3、5x5)和池化操作来提取多尺度特征。以下是…...
day32 学习笔记
文章目录 前言一、霍夫变换二、标准霍夫变换三、统计概率霍夫变换四、霍夫圆变换 前言 通过今天的学习,我掌握了霍夫变换的基本原本原理及其在OpenCV中的应用方法 一、霍夫变换 霍夫变换是图像处理中的常用技术,主要用于检测图像中的直线,圆…...
2025时间序列都有哪些创新点可做——总结篇
作为AI和数据科学的核心方向之一,时间序列在2025年依然保持着强劲的发展势头,稳站各大顶会顶刊投稿主题前列。 关于它的研究,目前在结合传统统计方法和深度学习的基础上,已延伸至频域等数理工具与神经网络的交叉创新。同时针对垂…...
头歌实训之索引
🌟 各位看官好,我是maomi_9526! 🌍 种一棵树最好是十年前,其次是现在! 🚀 今天来学习C语言的相关知识。 👍 如果觉得这篇文章有帮助,欢迎您一键三连,分享给更…...
通讯的基础概念:涵盖串行通信、并行通信、TCP、UDP、Socket 等关键概念和技术
一、通信基础概念 1. 串行通信与并行通信 串行通信 定义:通过一条线路逐位传输数据,每个字节包含起始位、数据位、校验位和停止位。特点: 传输稳定,但速度较慢(因逐位传输)。常用接口:RS-232、…...
Uni-App 多端电子合同开源项目介绍
项目概述 本项目是一款基于 uni-app框架开发的多端电子合同管理平台,旨在为企业及个人用户提供高效、安全、便捷的电子合同签署与管理服务。项目创新性地引入了 “证据链”与“非证据链”两种签署模式,满足不同场景下的签署需求,支持多种签署…...
一个非常快速的 Latex 入门教程【Part 1】
目录 1.LaTex简介 2.LaTex 中最基础的格式化命令 2.1加粗,斜体,下划线,添加新段落 2.2文档分节 2.3 图片 2.4 LaTeX 中列表的创建 无序列表 有序列表 2.5对数学公式的排版 2.6表格 1.LaTex简介 LaTex的主要优势是它会将文…...
用Obsidian四个插件打造小说故事关联管理系统:从模板到图谱的全流程实践
用Obsidian四个插件打造小说故事关联管理系统:从模板到图谱的全流程实践 一、前言:为什么需要故事关联管理系统 在小说创作中,复杂的人物关系、交错的情节线和多维的世界观常导致创作混乱。本文将通过 Dataview(数据查询…...
C++ 日志系统实战第三步:熟悉掌握各种设计模式
全是通俗易懂的讲解,如果你本节之前的知识都掌握清楚,那就速速来看我的项目笔记吧~ 相关技术知识补充,也是最后的补充知识了~ 下文将加入项目代码编写! 目录 设计模式 单例模式 饿汉模式 懒汉模式 工厂模式 简单…...
[ESP-IDF]:esp32-camera 使用指南 ESP32S3-OV2640 用例测试
【核知坊】:释放青春想象,码动全新视野。 我们希望使用精简的信息传达知识的骨架,启发创造者开启创造之路!!! 内容摘要:esp32-camera 组件为 ESP32 系列 SoC 提供了兼容的图…...
在统信UOS/麒麟Kylin OS中创建网页桌面快捷方式
在统信UOS/麒麟Kylin OS中创建网页桌面快捷方式 本文将详细介绍如何在统信UOS或麒麟KYLINOS中使用命令行创建一个网页桌面快捷方式,以方便构建云桌面模板及镜像模板。欢迎大家浏览、分享和转发!请关注我以获取更多技术分享。 1. 查看系统信息 首先&am…...
SQLite 是什么?
📌 一、SQLite 是什么? SQLite 是一个轻量级、嵌入式数据库,意思是它直接集成在你的 App 内部,不需要单独安装数据库服务端。 ✅ 特点: 特点说明本地使用所有数据保存在手机内部存储文件形式数据以 .db 文件形式存储…...
恒创科技「香港大带宽云」新老用户专享实例及热门配置
全球化数字浪潮下,高带宽应用正深度重构各行业运营模式——从跨境电商、流媒体与视频点播,到在线游戏与云游戏加速,涵盖所有高并发、强交互的业务场景。在此背景下,企业对高性能 IT 基础架构的需求持续升级,以此来支持…...
fpga系列 HDL:verilog latch在fpga中的作用 避免latch的常见做法
目录 Latch在FPGA中的作用Quartus中有关latch的警告⚠避免Latch的常见做法1. if-else 语句未覆盖所有条件生成Latch的代码:修复后的代码: 2. case语句未覆盖所有分支生成Latch的代码:修复后的代码: 3. 组合逻辑中缺少默认赋值生成…...
java配置
环境变量...
解决虚拟主机ping不通本地主机问题
win11 1 问题 虚拟主机和本地主机在同一网段。 2 解决方案 以win11为例: 设置 -> 网络和 Internet -> 高级网路设置 -> Windows 防火墙 -> 高级设置 -> 入站规则 -> 新建规则 需要设置:规则类型、 协议和端口、名称,其…...
Move Registry 发布,实现 Sui 的超级互操作性
Move Registry(MVR)的到来对 Sui 来说是一件大事。MVR 是一个功能齐全的链上包管理系统,提升了整个生态的可发现性、可信度和互操作性。Sui 本身就是最具互操作性的链之一,凭借 Move 语言和可编程交易区块(PTBs&#x…...
【Linux】gdb工具,Linux 下程序调试的 “透视眼”
目录 调试代码调试注意事项gdb和Cgdb调试命令汇总行号显示断点设置查看断点信息删除断点开启 / 禁用断点运行 / 调试逐过程和逐语句打印 / 追踪变量指定行号跳转强制执行函数 补充命令watchset var 替换变量值条件断点 end 调试代码 这是本次调试要用的代码 1 #include <st…...
脚本分享:快速作图对比wannier拟合能带python脚本
本脚本通过Python实现电子能带结构数据的快速作图,能够从两个不同的数据文件(BAND.dat 和 wannier90_band.dat)中提取有效数据,并在同一坐标系下绘制对比图。 准备工作:使用VASPKIT处理获得能带数据BAND.datÿ…...
解决ssh拉取服务器数据,要多次输入密码的问题
问题在于,每次循环调用 rsync 都是新开一个连接,所以每次都需要输入一次密码。为了只输入一次密码,有以下几种方式可以解决: ✅ 推荐方案:设置 SSH 免密登录 最稳最安全的方式是:配置 SSH 免密登录&#x…...
金仓数据库 KingbaseES 产品深度优化提案:迈向卓越的全面升级
文章目录 一、引言二、性能优化(一)查询性能提升1. 优化查询优化器引入基于代价的查询优化算法支持更多的查询优化提示 2. 索引优化支持更多类型的索引优化索引的创建和维护策略 (二)并发处理能力增强1. 锁机制优化采用更细粒度的…...
企业级智能合同管理解决方案升级报告:道本科技携手DeepSeek打造智能合同管理新标杆
当传统合同管理系统还在与堆积如山的纸质文档较劲时,道本科技与DeepSeek联合开发的智能合同平台已为国央企打开新视界。我们以某大型能源集团的实际应用为例,带您直观感受技术升级带来的管理变革。 一、技术升级的具象化呈现 在未接入DeepSeek技术前&a…...
C#并行编程极大提升集合处理速度,再也没人敢说你程序性能差了!
马工撰写的年入30万C#上位机项目实战必备教程(点击下方链接即可访问文章目录) 1、《C#串口通信从入门到精通》 2、《C#与PLC通信从入门到精通 》 3、《C# Modbus通信从入门到精通》 4、《C#Socket通信从入门到精通 》 5、《C# MES通信从入门到精通》 6、…...
[贪心_7] 最优除法 | 跳跃游戏 II | 加油站
目录 1.最优除法 题解 2.跳跃游戏 II 题解 3.加油站 题解 利用 单调性,可以实现 区间跳跃 1.最优除法 链接: 553. 最优除法 给定一正整数数组 nums,nums 中的相邻整数将进行浮点除法。 例如,nums [2,3,4],我…...
【Rust】Rust中的枚举与模式匹配,原理解析与应用实战
✨✨ 欢迎大家来到景天科技苑✨✨ 🎈🎈 养成好习惯,先赞后看哦~🎈🎈 🏆 作者简介:景天科技苑 🏆《头衔》:大厂架构师,华为云开发者社区专家博主,…...
【CUDA 编译 bug】ld: cannot find -lcudart
我们使用 Conda 安装 pytorch 和 CUDA 环境之后,要用 Conda 的CUDA环境进行某个库编译时,出现了bug: /mnt/data/home/xxxx/miniforge3/envs/GAGAvatar/compiler_compat/ld: cannot find -lcudart: No such file or directorycollect2: error…...
MYSQL之数据类型
数据类型分类 数值类型 在MySQL中, 整型可以指定是有符号的和无符号的, 默认是有符号的. 可以通过 UNSIGNED 来说明某个字段是无符号的. tinyint类型 以tinyint为例, 其它的整型类型都只是数据范围的区别. 数据越界 创建一个 tinyint 类型的 num 的属性, 大小为 1 字节, 不…...
Asp.Net Core 异常筛选器ExceptionFilter
文章目录 前言一、异常筛选器的核心概念用途:实现接口:执行时机: 二、使用步骤1.创建自定义异常筛选器2.注册异常筛选器全局注册(对所有 Controller 生效):局部注册(通过特性标记特定的 **Contr…...
WebUI可视化:第2章:技术基础准备
学习目标 ✅ 掌握HTML/CSS基础语法 ✅ 理解JavaScript核心功能 ✅ 了解前后端交互原理 2.1 HTML基础:网页的骨架 2.1.1 基础结构 每个HTML文件都必须包含以下基本结构: html <!DOCTYPE html> <html> <head><title>我的第一个网页</title> …...
Java基础集合 面试经典八股总结 [连载ing]
序言 八股,怎么说呢。我之前系统学习的内容,进行梳理。通过问题的方式,表达出得当的内容,这件事本身就很难。面试时心态、状态、掌握知识的情况等。关于八股文,我不想有太多死记硬背的内容,更多的是希望自我…...
大数据运维面试题
华为大数据运维面试题可能涵盖多个方面,以下是一些可能的面试问题及解析,这些问题旨在考察应聘者的技术知识、问题解决能力和对大数据运维的理解: 一、技术知识类问题 简述大数据运维的主要职责和工作内容 回答示例:大数据运维工…...
OpenBMC:BmcWeb login认证
BmcWeb在include\login_routes.hpp中实现了/login用于完成web的登录: BMCWEB_ROUTE(app, "/login").methods(boost::beast::http::verb::post)(handleLogin);inline void handleLogin(const crow::Request& req,const std::shared_ptr<bmcweb::AsyncResp>…...
Python学习之路(五)-接口API
在 Python 中结合数据库开发接口 API 通常使用 Web 框架(如 Flask 或 Django)和 ORM(对象关系映射)工具(如 SQLAlchemy 或 Django ORM)。以下是使用 Flask 和 SQLAlchemy 的详细步骤,展示如何结合数据库开发一个简单的 API。 使用 Flask 和 SQLAlchemy 开发 API 1. 安…...
数据库+Docker+SSH三合一!深度评测HexHub的全栈开发体验
作为一名技术博主,我最近一直被各种开发工具切换搞得焦头烂额。数据库要用Navicat,服务器管理得开Termius,Docker操作还得切到命令行,每天光在不同工具间切换就浪费了大量时间。直到团队里的一位架构师向我推荐了HexHub这个一体化…...
涂料油墨制造数字化转型的关键技术与挑战
涂料油墨制造行业正处于数字化转型的关键时期,这一转型是提升生产效率、增强产品质量和降低成本的重要途径。以下是该行业在数字化转型中的关键技术与面临的挑战: 关键技术: 工业互联网技术:通过在生产设备上安装传感器…...
UE5 调整字体、界面大小
文章目录 方案一 5.4 版本及以上(推荐)方案二 5.3 版本及以下(推荐)方案三 使用插件(不推荐) 方案一 5.4 版本及以上(推荐) 进入 编辑 > 编辑器偏好设置,如下图所示&…...
【OpenCV图像处理实战】从基础操作到工业级应用
目录 前言技术背景与价值当前技术痛点解决方案概述目标读者说明 一、技术原理剖析核心概念图解核心作用讲解关键技术模块说明技术选型对比 二、实战演示环境配置要求核心代码实现(6个案例)案例1:图像基本操作案例2:边缘检测案例3&…...
生成随机验证码-解析与优化
文章目录 代码功能解析潜在问题与优化建议1. 安全性问题2. 易混淆字符过滤3. 参数校验4. 性能优化 扩展功能示例1. 自定义字符集2. 批量生成验证码 完整优化代码关键总结 代码功能解析 import random import stringdef generate_code(length6):chars string.digits string.a…...
VMware 虚拟机镜像资源网站
常见的 VMware 虚拟机镜像资源网站 网站名称链接地址特点OSBoxes.orgOSBoxes - Virtual Machines for VirtualBox & VMware 提供 .vmx .vmdk,适合 VMware 和 VirtualBox,更新频率高,界面清晰LinuxVMImages.comLinux VM Images - Downlo…...
HTML5 详细学习笔记
1. HTML5 简介 HTML5 是最新的 HTML 标准,于 2014 年 10 月由 W3C 完成标准制定。它增加了许多新特性,包括语义化标签、多媒体支持、图形效果、离线存储等。 1.1 HTML5 文档基本结构 <!DOCTYPE html> <html lang"zh-CN"> <h…...
真.从“零”搞 VSCode+STM32CubeMx+C <1>构建
目录 前言 准备工作 创建STM32CubeMx项目 VSCode导入项目&配置 构建错误调试 后记 前言 去年10月开始接触单片机,一直在用树莓派的Pico,之前一直用Micropython,玩的不亦乐乎,试错阶段优势明显,很快就能鼓捣一…...
Pikachu靶场
本质是信任了不可信的客户端输入。防御核心: 永不信任客户端提交的权限参数(如 user_id, role)。强制服务端校验用户身份与操作权限。定期审计权限模型,避免业务迭代引入新漏洞。 水平越权 1,按照网站的提示要求登录 进…...
五、web自动化测试01
目录 一、HTML基础1、HTML介绍2、常用标签3、基础案例3.1 前端代码3.2 自动化测试 二、CSS定位1、css介绍2、案例3、代码优化 三、表单自动化1、案例2、元素属性定位 四、后台基础数据自动化1、登录1.1 id与class定位1.2 定位一组元素 2、商品新增 一、HTML基础 可参考学习 链…...
利用软件I2C驱动OLED,点亮、熄灭OLED屏幕以及获取当前OLED屏幕开启状态
题目: 参考《I2C通信》的文档,自行连接电路,利用软件I2C驱动OLED,点亮、熄灭OLED屏幕以及获取当前OLED屏幕开启状态。 可以优先实现: 软件I2C初始化函数,用于初始化IO引脚 再实现: 主机发起始位和停止位,主机发送1个字节,…...
数据结构——栈与队列
1.栈 1.1概念 一种特殊的线性表,其只允许在固定的一端进行插入和删除元素操作。 进行数据插入和删除操作的一端 称为栈顶,另一端称为栈底。 栈中的数据元素遵守后进先出 LIFO ( Last In First Out )的原则。 压栈:栈…...
【嵌入式系统设计师(软考中级)】第二章:嵌入式系统硬件基础知识(3)
文章目录 4. 嵌入式系统I/O接口4.1 GPIO与PWM接口4.1.1 GPIO接口(General-Purpose Input/Output)4.1.2 PWM接口(Pulse Width Modulation) 4.2 A/D与D/A接口的基本原理与结构4.2.1 DA转换(数模转换,Digital-…...
【网络安全】社会工程学策略
1. 社会工程学简介 社会工程攻击是威胁行为者常用的攻击方式。这是因为,诱骗人们提供访问权限、信息或金钱通常比利用软件或网络漏洞更容易。 您可能还记得,社会工程学是一种利用人为错误来获取私人信息、访问权限或贵重物品的操纵技术。它是一个涵盖性…...
ROS2---时间戳对齐
一、ROS2时间系统架构 时间模型 仿真时间(Simulation Time):由/clock话题驱动,适用于离线仿真与调试。真实时间(Real Time):基于系统硬件时钟,支持PTP协议(IEEE 1588&…...
C语言教程(十五):C 语言函数指针与回调函数详解
一、函数指针 1.1 函数指针的概念 在 C 语言中,函数指针是指向函数的指针变量。每个函数在内存中都有一个起始地址,函数指针就存储了这个起始地址,通过函数指针可以调用相应的函数。 1.2 函数指针的定义 函数指针的定义语法如下:返…...
VSCode如何修改默认扩展路径和用户文件夹目录到其他盘以及微信开发工具如何修改扩展路径到其他盘
ps:因公司电脑c盘内存严重不足,而出本篇文章 1.Visual Studio Code 随着VsCode的使用时间的推移,安装的扩展以及数据逐步增多,导致c盘内存占用较大,所以这里将vscode的默认缓存路径等迁移到其他盘。 步骤如下 1.找到默认的存储…...