YOLOv3的改进思路与方法:解析技术难点与创新突破
YOLOv3作为目标检测领域的经典算法,凭借其出色的速度和性能平衡获得了广泛应用。然而,随着计算机视觉技术的不断发展,YOLOv3在某些场景下的局限性也逐渐显现。本文将深入分析YOLOv3的不足之处,并系统介绍常见的改进策略和方法,帮助初学者更好地理解和应用这些改进技术。
YOLOv3的主要不足之处
1. 小目标检测性能不佳
尽管YOLOv3相比前代有了显著提升,但在检测小目标时仍然存在明显劣势。特别是在密集场景中,小目标的检测召回率较低,这主要是因为特征提取过程中的下采样操作导致空间信息损失。
2. 特征融合机制有限
YOLOv3虽然采用了FPN(特征金字塔网络)结构进行多尺度特征融合,但其融合方式相对简单,主要是通过上采样和特征拼接实现,未能充分利用不同层级特征间的互补关系。
3. 对遮挡、变形目标检测不足
当目标被部分遮挡或发生较大形变时,YOLOv3的检测性能会大幅下降,这是由于其特征表示能力有限,无法很好地捕捉这些复杂变化。
4. 网络结构优化空间
YOLOv3的主干网络Darknet-53虽然性能不错,但在计算效率和特征提取能力方面仍有优化空间,特别是与当前最新的网络架构相比。
5. 锚框设计不够灵活
预定义的锚框(anchor boxes)设计难以适应所有场景,尤其是在目标形状变化大或分布不均匀的数据集上,固定的锚框设计会限制检测性能。
YOLOv3的改进策略与方法
1. 特征提取网络优化
1.1 引入更强大的主干网络
替代Darknet-53的常见选择:
- ResNet系列(ResNet50/101):更深层次的特征提取
- EfficientNet:平衡计算效率和性能
- CSPDarknet:跨阶段部分连接的改进版Darknet
这些替代网络通常能提供更丰富的特征表示,同时在计算量和性能之间找到更好的平衡点。
1.2 注意力机制集成
在特征提取过程中引入注意力机制,可以帮助网络关注更重要的空间区域或通道:
- 空间注意力(Spatial Attention):强化对目标区域的关注
- 通道注意力(Channel Attention):突出重要的特征通道
- CBAM(Convolutional Block Attention Module):结合空间和通道注意力
2. 特征融合机制增强
2.1 改进的特征金字塔结构
标准FPN的改进版本:
- PANet(Path Aggregation Network):增加自底向上的路径,增强特征传递
- BiFPN(Bidirectional Feature Pyramid Network):双向特征融合,并添加加权机制
- ASFF(Adaptive Spatial Feature Fusion):自适应空间特征融合
2.2 深度特征聚合
采用更复杂的特征聚合策略,如:
# 示例代码:深度可分离卷积的特征融合
def feature_fusion(low_level_feat, high_level_feat):# 上采样高层特征high_level_upsampled = F.interpolate(high_level_feat, size=low_level_feat.shape[2:],mode='bilinear', align_corners=False)# 深度可分离卷积处理低层特征low_level_processed = self.depthwise_separable_conv(low_level_feat)# 特征融合(加权融合而非简单相加)fused_features = self.fusion_weights[0] * low_level_processed + \self.fusion_weights[1] * high_level_upsampledreturn self.post_fusion_conv(fused_features)
3. 小目标检测增强策略
3.1 多尺度特征增强
- 添加更多检测头:在更高分辨率的特征图上增加检测头
- 特征图上采样:保留更多空间细节信息
- 密集连接:增加不同层级特征图之间的连接
3.2 数据增强技术
针对小目标检测的特殊数据增强方法:
- Mosaic数据增强:将四张图片拼接为一张,增加小目标数量
- MixUp:混合两张图片及其标签
- 随机缩放:随机改变图像尺寸,使模型适应不同大小的目标
4. 锚框优化策略
4.1 自适应锚框生成
通过聚类算法针对特定数据集生成更合适的锚框尺寸:
# 示例代码:使用K-means优化锚框
def optimize_anchors(annotation_dims, n_anchors=9):"""使用K-means聚类优化锚框尺寸annotation_dims: 数据集中所有边界框的宽高n_anchors: 需要生成的锚框数量"""from sklearn.cluster import KMeans# 运行K-means聚类kmeans = KMeans(n_clusters=n_anchors, random_state=0).fit(annotation_dims)anchors = kmeans.cluster_centers_# 根据面积排序areas = anchors[:, 0] * anchors[:, 1]indices = np.argsort(areas)return anchors[indices]
4.2 无锚框设计
完全抛弃锚框的设计,直接在特征图上预测目标的中心点和尺寸:
- CenterNet:检测目标中心点,然后回归其他属性
- FCOS(Fully Convolutional One-Stage):逐像素预测,无需锚框
5. 损失函数改进
5.1 IOU损失系列
改进的边界框回归损失:
- GIoU Loss:考虑未重叠区域的几何信息
- DIoU Loss:额外考虑中心点距离
- CIoU Loss:同时考虑重叠面积、中心点距离和长宽比
# CIoU Loss实现示例
def ciou_loss(pred_boxes, target_boxes):# 计算边界框的坐标pred_x1, pred_y1, pred_x2, pred_y2 = pred_boxes[..., 0], pred_boxes[..., 1], \pred_boxes[..., 2], pred_boxes[..., 3]target_x1, target_y1, target_x2, target_y2 = target_boxes[..., 0], target_boxes[..., 1], \target_boxes[..., 2], target_boxes[..., 3]# 计算面积pred_area = (pred_x2 - pred_x1) * (pred_y2 - pred_y1)target_area = (target_x2 - target_x1) * (target_y2 - target_y1)# 计算IoUintersect_x1 = torch.max(pred_x1, target_x1)intersect_y1 = torch.max(pred_y1, target_y1)intersect_x2 = torch.min(pred_x2, target_x2)intersect_y2 = torch.min(pred_y2, target_y2)intersect_area = torch.clamp(intersect_x2 - intersect_x1, 0) * \torch.clamp(intersect_y2 - intersect_y1, 0)union_area = pred_area + target_area - intersect_areaiou = intersect_area / union_area# 计算外接矩形的对角线距离enclose_x1 = torch.min(pred_x1, target_x1)enclose_y1 = torch.min(pred_y1, target_y1)enclose_x2 = torch.max(pred_x2, target_x2)enclose_y2 = torch.max(pred_y2, target_y2)enclose_diagonal = (enclose_x2 - enclose_x1)**2 + (enclose_y2 - enclose_y1)**2# 计算中心点距离center_x1 = (pred_x1 + pred_x2) / 2center_y1 = (pred_y1 + pred_y2) / 2center_x2 = (target_x1 + target_x2) / 2center_y2 = (target_y1 + target_y2) / 2center_distance = (center_x1 - center_x2)**2 + (center_y1 - center_y2)**2# 计算宽高比一致性惩罚项v = 4 / (np.pi ** 2) * torch.pow(torch.atan((pred_x2 - pred_x1) / (pred_y2 - pred_y1)) - torch.atan((target_x2 - target_x1) / (target_y2 - target_y1)), 2)alpha = v / (1 - iou + v)# 计算CIoUciou = iou - center_distance / enclose_diagonal - alpha * vreturn 1 - ciou
5.2 标签分配策略
优化正负样本分配机制:
- ATSS(Adaptive Training Sample Selection):自适应选择正样本
- OTA(Optimal Transport Assignment):基于最优传输理论的标签分配
- SimOTA:简化版最优传输分配方法
6. 后处理优化
6.1 改进的NMS方法
- Soft-NMS:逐渐降低重叠框的置信度,而非直接抑制
- DIoU-NMS:使用DIoU度量替代IoU进行NMS
- Weighted-NMS:基于权重的非极大值抑制
# Soft-NMS实现示例
def soft_nms(boxes, scores, iou_threshold=0.5, soft_threshold=0.001, sigma=0.5, method='gaussian'):"""实现Soft-NMSboxes: 边界框坐标 [N, 4]scores: 置信度分数 [N]"""N = boxes.shape[0]indices = np.arange(N)# 按分数降序排序sorted_idx = np.argsort(scores)[::-1]boxes = boxes[sorted_idx]scores = scores[sorted_idx]indices = indices[sorted_idx]# 应用Soft-NMSfor i in range(N):if scores[i] < soft_threshold:continuefor j in range(i+1, N):if scores[j] < soft_threshold:continue# 计算IoUiou = calculate_iou(boxes[i], boxes[j])# 应用软化策略if method == 'linear':if iou > iou_threshold:scores[j] *= (1 - iou)elif method == 'gaussian':scores[j] *= np.exp(-(iou * iou) / sigma)# 按新分数重新排序sorted_idx = np.argsort(scores)[::-1]keep = indices[sorted_idx[scores[sorted_idx] > soft_threshold]]return keep
6.2 预测结果优化
- 测试时增强(Test-Time Augmentation, TTA):多角度、多尺度测试
- 模型集成:融合多个模型的预测结果
- 级联检测:多阶段细化检测结果
实际应用中的改进实例
实例一:YOLOv3-SPP
通过加入空间金字塔池化(Spatial Pyramid Pooling)模块,增强了网络对不同尺度特征的捕获能力:
# SPP模块实现示例
class SpatialPyramidPooling(nn.Module):def __init__(self, in_channels, out_channels, kernel_sizes=[5, 9, 13]):super(SpatialPyramidPooling, self).__init__()self.maxpools = nn.ModuleList([nn.MaxPool2d(kernel_size=k, stride=1, padding=k//2)for k in kernel_sizes])self.conv = nn.Conv2d(in_channels * (len(kernel_sizes) + 1), out_channels,kernel_size=1,stride=1,padding=0)def forward(self, x):features = [x]features.extend([maxpool(x) for maxpool in self.maxpools])return self.conv(torch.cat(features, dim=1))
实例二:YOLOv3-Tiny优化
针对资源受限设备的轻量级优化:
- 使用深度可分离卷积替代标准卷积
- 知识蒸馏:使用完整YOLOv3模型指导小模型学习
- 通道剪枝:移除冗余通道,减少参数量
实例三:YOLOv3结合DeepSORT的多目标跟踪
将YOLOv3检测结果与DeepSORT跟踪算法结合,实现视频中的目标跟踪:
# YOLOv3+DeepSORT实现伪代码
def track_objects_in_video(video_path, yolo_model, deepsort_tracker):cap = cv2.VideoCapture(video_path)while True:ret, frame = cap.read()if not ret:break# 使用YOLOv3检测目标detections = yolo_model.detect(frame)# 转换检测结果为DeepSORT所需格式boxes = [det[:4] for det in detections]scores = [det[4] for det in detections]class_ids = [det[5] for det in detections]# 使用DeepSORT进行跟踪tracking_results = deepsort_tracker.update(boxes, scores, class_ids, frame)# 绘制跟踪结果for track in tracking_results:bbox, track_id, class_id = track[0:4], track[4], track[5]draw_tracking_info(frame, bbox, track_id, class_id)cv2.imshow('Tracking', frame)if cv2.waitKey(1) & 0xFF == ord('q'):breakcap.release()cv2.destroyAllWindows()
如何将这些改进应用到自己的项目中
1. 分析问题
首先需要明确当前YOLOv3在你的应用场景中存在的具体问题:
- 是检测小目标性能不佳?
- 是计算资源受限需要轻量化?
- 是特定场景下的检测精度不够?
2. 选择合适的改进策略
根据问题选择相应的改进方法:
问题 -> 可能的解决方案:
- 小目标检测不佳 -> 特征融合增强 + 数据增强
- 计算资源有限 -> 网络剪枝 + 知识蒸馏
- 特定场景精度不足 -> 针对性数据增强 + 损失函数优化
- 检测速度要求高 -> 轻量级主干网络 + 模型量化
3. 实施改进步骤
- 建立基线:首先训练标准YOLOv3模型,记录性能指标
- 逐步引入改进:每次只引入一种改进,评估其效果
- 调整超参数:针对引入的改进方法调整相关超参数
- 模型验证:在验证集上全面评估模型性能
- 综合优化:将有效的改进方法组合并进行整体优化
4. 注意事项
- 避免过拟合:引入复杂改进时需要注意模型泛化能力
- 平衡计算量与性能:不要盲目堆叠改进方法
- 针对性优化:根据应用场景有选择地应用改进策略
- 充分验证:在多种测试场景下验证改进效果
总结
YOLOv3尽管已经是一个相当强大的目标检测算法,但通过针对性的改进,我们可以进一步提升其性能。本文介绍的改进策略涵盖了特征提取网络优化、特征融合增强、小目标检测增强、锚框优化、损失函数改进以及后处理优化等多个方面。
初学者可以根据自己的具体应用场景和问题,选择性地应用这些改进方法。重要的是理解每种改进的原理和适用情况,而不是盲目堆叠多种技术。通过系统化的实验和验证,你可以找到最适合自己项目的YOLOv3改进组合,从而实现更好的目标检测性能。
希望本文能为你在深入理解和改进YOLOv3算法的路上提供有价值的参考和指导。随着计算机视觉技术的不断发展,我们也期待看到更多创新的改进方法出现。
相关文章:
YOLOv3的改进思路与方法:解析技术难点与创新突破
YOLOv3作为目标检测领域的经典算法,凭借其出色的速度和性能平衡获得了广泛应用。然而,随着计算机视觉技术的不断发展,YOLOv3在某些场景下的局限性也逐渐显现。本文将深入分析YOLOv3的不足之处,并系统介绍常见的改进策略和方法&…...
【解锁元生代】ComfyUI工作流与云原生后端的深度融合:下一代AIGC开发范式革命
## 从单机到云原生的认知跃迁 当2023年Stable Diffusion WebUI还在争夺本地显卡性能时,ComfyUI已悄然开启工作流模块化革命;当2024年AI绘画工具陷入"参数调优内卷",云原生技术正重塑AI开发的基础设施层。二者的深度融合࿰…...
shell 编程之正则表达式与文本处理器
目录 一、正则表达式 1. 概念 2. 作用 3. 分类 二、基础正则表达式(BRE) grep 命令选项 三、扩展正则表达式(ERE) 与 BRE 的区别 四、文本处理器 1. sed 工具 2. awk 工具 五、总结 总结对比 元字符总结 工具对比与…...
Shell编程之正则表达式与文本处理器
目录 一、引言 二、正则表达式 2.1 定义与用途 2.2 基础正则表达式 2.2.1 查找特定字符 2.2.2 利用中括号 “[]” 查找集合字符 2.2.3 查找行首 “^” 与行尾字符 “$” 2.2.4 查找任意一个字符 “.” 与重复字符 “*” 2.2.5 查找连续字符范围 “{}” 2.3 元字符总结…...
TMDOG——语言大模型进行意图分析驱动后端实践
语言大模型进行意图分析驱动后端实践 项目概述 项目地址:https://github.com/TMDOG666/AI_Backend_Demo 该项目通过语言大模型,通过分析用户意图、拆分任务、构建API调用链来驱动后端实践。 以一个简单的教务系统后端为例,将教务系统后端…...
未启用CUDA支持的PyTorch环境** 中使用GPU加速解决方案
1. 错误原因分析 根本问题:当前安装的PyTorch是CPU版本,无法调用GPU硬件加速。当运行以下代码时会报错:model YOLO("yolov8n.pt").to("cuda") # 或 .cuda()2. 解决方案步骤 步骤1:验证CUDA可用性 在Pyth…...
【mysql】Mac 通过 brew 安装 mysql 、启动以及密码设置
Mac 通过 brew 安装 mysql 、启动以及密码设置 使用 brew 安装 mysqlmysql 启动mysql密码设置参考文章: 使用 brew 安装 mysql brew install mysqlmysql 启动 下载完毕,终端告诉我们mysql数据库没有设置密码的,我们可以直接执行 mysql -u r…...
Vue2 nextTick
核心源码位置 Vue 2 的 nextTick 实现主要在 src/core/util/next-tick.js 文件中。 完整源码结构 import { noop } from shared/util import { handleError } from ./error import { isIE, isIOS, isNative } from ./envexport let isUsingMicroTask falseconst callbacks …...
Ubuntu 安装 NVIDIA显卡驱动、CUDA 以及 CuDNN工具
文章目录 一、简介二、查看显卡设备三、安装显卡驱动四、安装CUDA工具箱五、安装CuDNN小结 一、简介 NVIDIA 驱动:操作系统与 NVIDIA 显卡硬件之间的桥梁,负责驱动显卡硬件的运行,显卡的“底层操作系统”,一切的基础。CUDA&#…...
LeetCode算法题(Go语言实现)_50
题目 现有一个包含所有正整数的集合 [1, 2, 3, 4, 5, …] 。 实现 SmallestInfiniteSet 类: SmallestInfiniteSet() 初始化 SmallestInfiniteSet 对象以包含 所有 正整数。 int popSmallest() 移除 并返回该无限集中的最小整数。 void addBack(int num) 如果正整数 …...
idea报错java: 非法字符: ‘\ufeff‘解决方案
解决方案步骤以及说明 BOM是什么?1. BOM的作用2. 为什么会出现 \ufeff 错误?3. 如何解决 \ufeff 问题? 最后重新编译,即可运行!!! BOM是什么? \ufeff 是 Unicode 中的 BOM࿰…...
WPF依赖注入IHostApplicationLifetime关闭程序
WPF依赖注入IHostApplicationLifetime关闭程序 使用Application.Current.Shutdown();退出会报异常 应该使用 app.Dispatcher.InvokeShutdown(); Application.Current.Shutdown();app.Dispatcher.InvokeShutdown();static App app new();[STAThread]public static void Main(…...
如何在 IntelliJ IDEA 中安装通义灵码 - AI编程助手提升开发效率
随着人工智能技术的飞速发展,AI 编程助手已成为提升开发效率和代码质量的强大工具。在众多 AI 编程助手之中,阿里云推出的通义灵码凭借其智能代码补全、代码解释、生成单元测试等丰富功能,脱颖而出,为开发者带来了全新的编程体验。…...
【力扣】两两交换链表中的节点
两两交换链表中的节点 代码: /*** Definition for singly-linked list.* struct ListNode {* int val;* ListNode *next;* ListNode() : val(0), next(nullptr) {}* ListNode(int x) : val(x), next(nullptr) {}* ListNode(int x, ListNode *n…...
数据共享交换平台之文件交换
数据共享交换平台的文件交换管理功能提供部门与部门之间的文件交换通道,满足跨部门之间文件交换需求。文件交换需要能够按照交换业务场景对交换通道进行分类管理。文件交换管理需满足如下要求: 1.文件交换统计:支持查看本部门与其他部门之间…...
什么是全球代理?如何选择全球代理服务?
在全球化不断深化的今天,互联网已经成为人类沟通、工作和学习的重要纽带。而全球代理则是这一纽带上的关键技术之一,它赋予了我们探索不同地区网络资源的能力。今天,我们来聊聊什么是全球代理、它能做什么,以及如何选择合适的全球…...
Spring Boot整合Kafka的详细步骤
1. 安装Kafka 下载Kafka:从Kafka官网下载最新版本的Kafka。 解压并启动: 解压Kafka文件后,进入bin目录。 启动ZooKeeper:./zookeeper-server-start.sh ../config/zookeeper.properties。 启动Kafka:./kafka-server-…...
【正点原子STM32MP257连载】第四章 ATK-DLMP257B功能测试——USB WIFI测试 #WIFI蓝牙二合一 #RTL8733BU
1)实验平台:正点原子ATK-DLMP257B开发板 2)浏览产品:https://www.alientek.com/Product_Details/135.html 3)全套实验源码手册视频下载:正点原子资料下载中心 文章目录 第四章 ATK-DLMP257B功能测试——USB…...
Doip功能寻址走UDP协议
目前使用 connect()函数的UDP客户端 ,这里接收数据 解析的地方 查看一下。 如果使用 bind()、sendto()、recvfrom() 组合 那么返回值 和发送要在做调整,,根据业务需要后续在调整 其余的 和原来的 逻辑都是一样的,只是协议变了而已。 if serv…...
硬件电路设计之51单片机(2)
声明:绘制原理图和PCB的软件为嘉立创EDA。根据B站尚硅谷嵌入式之原理图&PCB设计教程学习所作个人用笔记。 目录 一、原理图详解 1、TypeC接口 (1)TypeC接口介绍 (2)TypeC原理图 2、5V转3.3V 3、单片机电源开…...
Deeplizard 深度学习课程(一)—— Pytorch 和 Tensor 简介
前言 该pytorch笔记参考deeplizard官方网站课程,有相应视频和博客,链接如下: deeplizardhttps://deeplizard.com/learn/video/v5cngxo4mIg 1.Pytorch 简介 PyTorch 是一个深度学习框架和一个科学计算包。PyTorch 的科学计算方面主要是 PyTo…...
Delphi HMAC算法
1. 前言 今天做一个三方接口,接口文档描述签名采用MD5,但是实际测试过程中,始终校验不通过,经过和三方沟通,才知道采用的是HMAC-MD5。由于Delphi7没有对HMAC的支持,则采用XE版本来支持。本次使用Delphi XE …...
Ubuntu服务器性能调优指南:从基础工具到系统稳定性提升
一、性能监控工具的三维应用 1.1 监控矩阵构建 通过组合工具搭建立体监控体系: # 实时进程监控 htop --sort-keyPERCENT_CPU# 存储性能采集 iostat -dx 2# 内存分析组合拳 vmstat -SM 1 | awk NR>2 {print "Active:"$5"MB Swpd:"$3"…...
深度解析C++开源OCR引擎:架构、编译优化与工业级部署指南
1. 引言:OCR技术演进与现状分析 光学字符识别(OCR)技术经历了从传统模式识别到深度学习的三代发展: 第一代:基于模板匹配(1970s-1990s) 第二代:特征提取+分类器(1990s-2010s) 第三代:端到端深度学习(2010s-至今) 当前工业界主流方案呈现"双轨制"发展态势…...
关于Newtonsoft.Json
历史 Newtonsoft.Json(也称为 Json.NET)是由 James Newton - King 开发的一个开源的 JSON 处理库,它于 2007 年首次发布。在早期,.NET 平台缺乏一个强大且灵活的 JSON 处理工具,Newtonsoft.Json 应运而生,…...
Spark-Sql编程(三)
一、数据加载与保存 通用方式:使用spark.read.load和df.write.save,通过format指定数据格式(如csv、jdbc、json等),option设置特定参数(jdbc格式下的url、user等),load和save指定路…...
CTF--好像需要管理员
一、原网页: 二、步骤: 1.扫描: 发现:robots.txt 2.打开robots.txt: 3.打开resul.php: 4.代码解析: if ($_GET[x]$password) //检查通过 URL 参数 x 传递的值是否等于变量 $password 的值 详…...
耀圣控制设备有限公司总经理李雨蔓的创业之路
破浪者李雨蔓:从零到行业标杆的铿锵之路 在浙江永嘉这片被誉为“中国泵阀之乡”的热土上,一位86年出生的女性企业家,用十年光阴书写了一段白手起家的传奇。她,是一曲关于勇气、智慧与匠心的赞歌。从技术员到行业标杆的缔造者&…...
Spring Boot JPA 开发之Not an entity血案
项目状况介绍 项目环境 JDK 21Spring Boot 3.4.3Hibernate: 6.6.13.Final项目描述 因为是微服务架构,项目层级如下 project-parent project-com project-A … project-X 其中: project-parent定义依赖库的版本project-com 定义了一些公用的方法和配置,包括持久层的配置。…...
什么是车规级MCU?STM32也能上车规级场景?
一、车规级MCU的定义 车规级MCU(Microcontroller Unit)是专为汽车电子系统设计的微控制器芯片,集成CPU、存储器、外设接口等功能模块,用于实现车辆控制、数据处理和实时响应。其核心特点包括: 高可靠性:需在…...
vue3.2 + element-plus 实现跟随input输入框的弹框,弹框里可以分组或tab形式显示选项
效果 基础用法(分组选项) 高级用法(带Tab栏) <!-- 弹窗跟随通用组件 SmartSelector.vue --> <template><div class"smart-selector-container"><el-popover :visible"visible" :w…...
go 指针接收者和值接收者的区别
go 指针接收者和值接收者的区别 指针接收者和值接收者的区别主要有两点: Go 中函数传参是传值,因此指针接收者传递的是接收者的指针拷贝,值接收者传递的是接收者的拷贝---在方法中指针接收者的变量会被修改,而值接收者的成员变量…...
部署qwen2.5-VL-7B
简单串行执行 from transformers import Qwen2_5_VLForConditionalGeneration, AutoProcessor from qwen_vl_utils import process_vision_info import torch, time, threadingdef llm(model_path,promptNone,imageNone,videoNone,imagesNone,videosNone,max_new_tokens2048,t…...
Go:测试
go test 工具 go test是 Go 语言包的测试驱动程序 ,包依据特定约定组织 。包目录中以_test.go结尾的文件是go test编译对象,而非go build的编译目标 。 特殊测试函数 在*_test.go文件中有三种特殊函数 : 功能测试函数:以Test为…...
用微信小程序制作一个性行为同意协议系统
用微信小程序制作一个性行为同意协议系统 用微信小程序制作一个性行为同意协议系统,具备查询、修改、增加和演示的Web功能。首先,我需要明确这个系统的核心功能和法律合规性。性同意是一个敏感且法律相关的话题,必须确保系统的设计符合法律法…...
leetcode 122. Best Time to Buy and Sell Stock II
题目描述 这道题可以用贪心思想解决。 本文介绍用动态规划解决。本题分析方法与第121题一样,详见leetcode 121. Best Time to Buy and Sell Stock 只有一点区别。第121题全程只能买入1次,因此如果第i天买入股票,买之前的金额肯定是初始金额…...
FairyGUI图标文字合批失败的原因
1)FairyGUI图标文字合批失败的原因 2)为什么Cubemap的内存占用超高 3)如何找到网格某个切面的中心点 4)为什么SafeZone在倒屏后方向相反 这是第428篇UWA技术知识分享的推送,精选了UWA社区的热门话题,涵盖了…...
C/C++ 通用代码模板
✅ C 语言代码模板(main.c) 适用于基础项目、算法竞赛或刷题: #include <stdio.h> #include <stdlib.h> #include <string.h> #include <stdbool.h> #include <math.h>// 宏定义区 #define MAX_N 1000 #defi…...
void MainWindow::on_btnOutput_clicked()为什么我在QT里面没有connect,也能触发点击效果
在 Qt 中,即使你没有显式调用 connect 函数,某些信号(如按钮的 clicked() 信号)仍然可以触发槽函数。这是因为 Qt 提供了一种自动连接机制,称为 自动连接(Auto-Connection)。以下是可能的原因和…...
基于YOLO11的车牌识别分析系统
【包含内容】 【一】项目提供完整源代码及详细注释 【二】系统设计思路与实现说明 【三】系统数据统计与可视化分析支持 【技术栈】 ①:系统环境:Windows/macOS/Linux ②:开发环境:Python 3.8 ③:技术栈&#x…...
openwebui搭建mcp
1、升级ollama https://github.com/ollama/ollama/blob/main/docs/faq.md curl -fsSL https://ollama.com/install.sh | shOllama 启动后,设置外网访问_ollama 外部访问-CSDN博客 ubuntu安装deepseek-CSDN博客 sudo vim /etc/systemd/system/ollama.serviceEnvi…...
邀请函 | 知从科技邀您共赴2025上海车展
2025上海车展将于4月23日至5月2日在国家会展中心(上海)盛大举行。本届车展以 “科技智驾未来”为主题,共同展示新能源汽车、智能驾驶等领域的最新技术与成果。 知从科技将携行业领先的软件产品与技术服务亮相于本次展览会,全方位…...
ESP32开发工具链选择指南:ESP-IDF vs PlatformIO vs Arduino
1. 引言 ESP32作为乐鑫(Espressif)推出的一款高性能Wi-Fi & Bluetooth双模芯片,凭借其强大的性能和丰富的生态,在物联网(IoT)领域广受欢迎。然而,开发ESP32时面临的一个关键问题是…...
【JAVA】bat文件启动jar场景获取bat文件路径的方法
一、推荐方案:参数传递法 步骤1:修改BAT脚本 echo off java -jar -Dbat.file"%~f0" your-app.jar %*关键参数说明: %~f0:获取BAT文件的完整路径%*:传递所有原始参数 步骤2:Java代码获取参数 …...
OpenLayers:extent与view extent 介绍
一、范围的概念 1.什么是范围? 在Openlayers中范围(Extent)是用于表示地理空间区域的一种概念。它通常由一个数字数组构成,数组中的内容为:[最小x坐标,最小y坐标,最大x坐标,最大y坐…...
Python开发一个简单的软件系统
用Python语言实现,具备录入学生成绩、查询成绩和显示所有成绩等基本功能。以下是代码: # 用于存储学生成绩的字典,键是学生姓名,值是成绩 student_scores {} # 录入学生成绩的函数 def input_scores(): name input("…...
小草GrassRouter多5G聚合路由设备在应急公安消防行业的解决方案及重要作用
小草GrassRouter多5G聚合路由设备在应急、公安、消防等行业的解决方案及重要作用主要体现在以下几个方面,这些领域对通信的高可靠性、高带宽、低时延需求尤为突出,尤其在复杂环境或突发事件中需要保障指挥调度的实时性和稳定性: ** 一、行业…...
冒泡排序、插入排序、快速排序、堆排序、希尔排序、归并排序
目录 冒泡排序插入排序快速排序(未优化版本)快速排序(优化版本)堆排序希尔排序归并排序各排序时间消耗对比 冒泡排序 冒泡排序核心逻辑就是对数组从第一个位置开始进行遍历,如果发现该元素比下一个元素大,则交换位置,如果不大,就…...
JVM知识
JVM 内存模型 JVM的内存模型介绍一下 根据 JVM8 规范,JVM 运行时内存共分为虚拟机栈、堆、方法区、程序计数器、本地方法栈五个部分。 JVM的内存结构主要分为以下几个部分: 方法区:存放类对象 Java 虚拟机栈:存放方法之间的调…...
Docker 中多个容器之间的通信
在 Docker 中,多个容器之间的通信可以通过以下几种主要方式实现,具体选择取决于网络需求、隔离性及管理复杂度: 一、自定义 Bridge 网络(推荐) 通过创建自定义的 Docker 网络,容器可以加入同一网络并通过容…...