C# Onnx yolov8-obb 旋转目标检测

目录

效果

模型信息

项目

代码

下载


C# Onnx Yolov8-OBB 旋转目标检测

效果

模型信息

Model Properties
-------------------------
date:2024-02-26T08:38:44.171849
description:Ultralytics YOLOv8s-obb model trained on runs/DOTAv1.0-ms.yaml
author:Ultralytics
task:obb
license:AGPL-3.0 https://ultralytics.com/license
version:8.1.18
stride:32
batch:1
imgsz:[640, 640]
names:{0: 'plane', 1: 'ship', 2: 'storage tank', 3: 'baseball diamond', 4: 'tennis court', 5: 'basketball court', 6: 'ground track field', 7: 'harbor', 8: 'bridge', 9: 'large vehicle', 10: 'small vehicle', 11: 'helicopter', 12: 'roundabout', 13: 'soccer ball field', 14: 'swimming pool'}
---------------------------------------------------------------

Inputs
-------------------------
name:images
tensor:Float[1, 3, 640, 640]
---------------------------------------------------------------

Outputs
-------------------------
name:output0
tensor:Float[1, 20, 8400]
---------------------------------------------------------------

项目

代码

using Microsoft.ML.OnnxRuntime;
using Microsoft.ML.OnnxRuntime.Tensors;
using OpenCvSharp;
using OpenCvSharp.Dnn;
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Linq;
using System.Numerics;
using System.Windows.Forms;namespace Onnx_Yolov8_Demo
{public partial class Form1 : Form{public Form1(){InitializeComponent();}string fileFilter = "*.*|*.bmp;*.jpg;*.jpeg;*.tiff;*.tiff;*.png";string image_path = "";string classer_path;DateTime dt1 = DateTime.Now;DateTime dt2 = DateTime.Now;string model_path;Mat image;Mat result_image;public string[] class_lables;SessionOptions options;InferenceSession onnx_session;Tensor<float> input_tensor;List<NamedOnnxValue> input_container;IDisposableReadOnlyCollection<DisposableNamedOnnxValue> result_infer;DisposableNamedOnnxValue[] results_onnxvalue;Tensor<float> result_tensors;private void button1_Click(object sender, EventArgs e){OpenFileDialog ofd = new OpenFileDialog();ofd.Filter = fileFilter;if (ofd.ShowDialog() != DialogResult.OK) return;pictureBox1.Image = null;image_path = ofd.FileName;pictureBox1.Image = new Bitmap(image_path);textBox1.Text = "";image = new Mat(image_path);pictureBox2.Image = null;}private void button2_Click(object sender, EventArgs e){if (image_path == ""){return;}button2.Enabled = false;pictureBox2.Image = null;textBox1.Text = "";Application.DoEvents();//图片缩放image = new Mat(image_path);int max_image_length = image.Cols > image.Rows ? image.Cols : image.Rows;Mat max_image = Mat.Zeros(new OpenCvSharp.Size(max_image_length, max_image_length), MatType.CV_8UC3);Rect roi = new Rect(0, 0, image.Cols, image.Rows);image.CopyTo(new Mat(max_image, roi));float[] result_array;float factor = (float)(max_image_length / 640.0);// 将图片转为RGB通道Mat image_rgb = new Mat();Cv2.CvtColor(max_image, image_rgb, ColorConversionCodes.BGR2RGB);Mat resize_image = new Mat();Cv2.Resize(image_rgb, resize_image, new OpenCvSharp.Size(640, 640));// 输入Tensorfor (int y = 0; y < resize_image.Height; y++){for (int x = 0; x < resize_image.Width; x++){input_tensor[0, 0, y, x] = resize_image.At<Vec3b>(y, x)[0] / 255f;input_tensor[0, 1, y, x] = resize_image.At<Vec3b>(y, x)[1] / 255f;input_tensor[0, 2, y, x] = resize_image.At<Vec3b>(y, x)[2] / 255f;}}//将 input_tensor 放入一个输入参数的容器,并指定名称input_container.Add(NamedOnnxValue.CreateFromTensor("images", input_tensor));dt1 = DateTime.Now;//运行 Inference 并获取结果result_infer = onnx_session.Run(input_container);dt2 = DateTime.Now;// 将输出结果转为DisposableNamedOnnxValue数组results_onnxvalue = result_infer.ToArray();// 读取第一个节点输出并转为Tensor数据result_tensors = results_onnxvalue[0].AsTensor<float>();result_array = result_tensors.ToArray();Mat result_data = new Mat(20, 8400, MatType.CV_32F, result_array);result_data = result_data.T();List<Rect2d> position_boxes = new List<Rect2d>();List<int> class_ids = new List<int>();List<float> confidences = new List<float>();List<float> rotations = new List<float>();// Preprocessing output resultsfor (int i = 0; i < result_data.Rows; i++){Mat classes_scores = new Mat(result_data, new Rect(4, i, 15, 1));OpenCvSharp.Point max_classId_point, min_classId_point;double max_score, min_score;// Obtain the maximum value and its position in a set of dataCv2.MinMaxLoc(classes_scores, out min_score, out max_score,out min_classId_point, out max_classId_point);// Confidence level between 0 ~ 1// Obtain identification box informationif (max_score > 0.25){float cx = result_data.At<float>(i, 0);float cy = result_data.At<float>(i, 1);float ow = result_data.At<float>(i, 2);float oh = result_data.At<float>(i, 3);double x = (cx - 0.5 * ow) * factor;double y = (cy - 0.5 * oh) * factor;double width = ow * factor;double height = oh * factor;Rect2d box = new Rect2d();box.X = x;box.Y = y;box.Width = width;box.Height = height;position_boxes.Add(box);class_ids.Add(max_classId_point.X);confidences.Add((float)max_score);rotations.Add(result_data.At<float>(i, 19));}}// NMS int[] indexes = new int[position_boxes.Count];CvDnn.NMSBoxes(position_boxes, confidences, 0.25f, 0.7f, out indexes);List<RotatedRect> rotated_rects = new List<RotatedRect>();for (int i = 0; i < indexes.Length; i++){int index = indexes[i];float w = (float)position_boxes[index].Width;float h = (float)position_boxes[index].Height;float x = (float)position_boxes[index].X + w / 2;float y = (float)position_boxes[index].Y + h / 2;float r = rotations[index];float w_ = w > h ? w : h;float h_ = w > h ? h : w;r = (float)((w > h ? r : (float)(r + Math.PI / 2)) % Math.PI);RotatedRect rotate = new RotatedRect(new Point2f(x, y), new Size2f(w_, h_), (float)(r * 180.0 / Math.PI));rotated_rects.Add(rotate);}result_image = image.Clone();for (int i = 0; i < indexes.Length; i++){int index = indexes[i];Point2f[] points = rotated_rects[i].Points();for (int j = 0; j < 4; j++){Cv2.Line(result_image, (OpenCvSharp.Point)points[j], (OpenCvSharp.Point)points[(j + 1) % 4], new Scalar(0, 255, 0), 2);}Cv2.PutText(result_image, class_lables[class_ids[index]] + "-" + confidences[index].ToString("0.00"),(OpenCvSharp.Point)points[0], HersheyFonts.HersheySimplex, 0.8, new Scalar(0, 0, 255), 2);}pictureBox2.Image = new Bitmap(result_image.ToMemoryStream());textBox1.Text = "推理耗时:" + (dt2 - dt1).TotalMilliseconds + "ms";button2.Enabled = true;}private void Form1_Load(object sender, EventArgs e){model_path = "model/yolov8s-obb.onnx";classer_path = "model/lable.txt";// 创建输出会话,用于输出模型读取信息options = new SessionOptions();options.LogSeverityLevel = OrtLoggingLevel.ORT_LOGGING_LEVEL_INFO;options.AppendExecutionProvider_CPU(0);// 设置为CPU上运行// 创建推理模型类,读取本地模型文件onnx_session = new InferenceSession(model_path, options);//model_path 为onnx模型文件的路径// 输入Tensorinput_tensor = new DenseTensor<float>(new[] { 1, 3, 640, 640 });// 创建输入容器input_container = new List<NamedOnnxValue>();List<string> str = new List<string>();StreamReader sr = new StreamReader(classer_path);string line;while ((line = sr.ReadLine()) != null){str.Add(line);}class_lables = str.ToArray();image_path = "test_img/1.png";pictureBox1.Image = new Bitmap(image_path);image = new Mat(image_path);}private void pictureBox1_DoubleClick(object sender, EventArgs e){Common.ShowNormalImg(pictureBox1.Image);}private void pictureBox2_DoubleClick(object sender, EventArgs e){Common.ShowNormalImg(pictureBox2.Image);}SaveFileDialog sdf = new SaveFileDialog();private void button3_Click(object sender, EventArgs e){if (pictureBox2.Image == null){return;}Bitmap output = new Bitmap(pictureBox2.Image);sdf.Title = "保存";sdf.Filter = "Images (*.jpg)|*.jpg|Images (*.png)|*.png|Images (*.bmp)|*.bmp|Images (*.emf)|*.emf|Images (*.exif)|*.exif|Images (*.gif)|*.gif|Images (*.ico)|*.ico|Images (*.tiff)|*.tiff|Images (*.wmf)|*.wmf";if (sdf.ShowDialog() == DialogResult.OK){switch (sdf.FilterIndex){case 1:{output.Save(sdf.FileName, ImageFormat.Jpeg);break;}case 2:{output.Save(sdf.FileName, ImageFormat.Png);break;}case 3:{output.Save(sdf.FileName, ImageFormat.Bmp);break;}case 4:{output.Save(sdf.FileName, ImageFormat.Emf);break;}case 5:{output.Save(sdf.FileName, ImageFormat.Exif);break;}case 6:{output.Save(sdf.FileName, ImageFormat.Gif);break;}case 7:{output.Save(sdf.FileName, ImageFormat.Icon);break;}case 8:{output.Save(sdf.FileName, ImageFormat.Tiff);break;}case 9:{output.Save(sdf.FileName, ImageFormat.Wmf);break;}}MessageBox.Show("保存成功,位置:" + sdf.FileName);}}}
}

下载

源码下载

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

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

相关文章

TextCNN:文本分类卷积神经网络

模型原理 1、前言2、模型结构3、示例3.1、词向量层3.2、卷积层3.3、最大池化层3.4、Fully Connected层 4、总结 1、前言 TextCNN 来源于《Convolutional Neural Networks for Sentence Classification》发表于2014年&#xff0c;是一个经典的模型&#xff0c;Yoon Kim将卷积神…

B站UP视频播放数据分析之然冉创业说

【背景介绍】 几年前做过类似的分析&#xff0c;但是B站数据加密了&#xff0c;刚好最近在用selenium&#xff0c;就顺手用它爬一下数据。 df pd.read_excel("然冉创业说_13.2万_output.xlsx") df.head() 以上数据在视频播放页面就可以获取到。 【数据分析】 从数…

sqli-labs(less-46)order by 注入

我们打开sql-labs的第46关然后在输入框内输入?id1时会发现页面没有任何的变化&#xff0c;此时我们用Visual Studio Code查看第46关的代码 此时我们发现sql语句是$sql "SELECT * FROM users ORDER BY $id"; &#xff0c;所以现在我们需要了解一下order by语句的作…

Helm vs Kustomize 深度比较

Helm和Kustomize都是流行的Kubernetes集群部署管理工具&#xff0c;本文比较了两者的优缺点&#xff0c;方便读者根据项目实际情况采用适合的方案。原文: Helm vs Kustomize: why, when, and how[1] 挑战 开始讨论之前&#xff0c;先来看看为什么要使用 Helm 或 Kustomize。 这…

AI数字人SadTalker实战

1.概述 AI数字人在营销和品牌推广中扮演着至关重要的角色&#xff0c;许多企业和个人正积极利用数字技术来打造属于自己的财富。有没有一种简单而免费的方式来创建自己的数字人呢&#xff1f;本篇博客笔者将为大家介绍如何搭建属于自己的AI数字人。 2.内容 2.1 什么是SadTalker…

Windows部署WebDAV服务并映射到本地盘符实现公网访问本地存储文件

文章目录 前言1. 安装IIS必要WebDav组件2. 客户端测试3. 使用cpolar内网穿透&#xff0c;将WebDav服务暴露在公网3.1 安装cpolar内网穿透3.2 配置WebDav公网访问地址 4. 映射本地盘符访问 前言 在Windows上如何搭建WebDav&#xff0c;并且结合cpolar的内网穿透工具实现在公网访…

【DL】深度学习之语音识别

目录 1 核心概念 2 安装依赖库 3 实践 语音信号处理&#xff08;Speech Signal Processing&#xff09;简称语音处理。 语音识别&#xff08;ASR&#xff09;和自然语言处理&#xff08;NLP&#xff09;&#xff1a;语音识别就是将语音信号转化成文字文本&#xff0c;简单实…

解决启动服务报./nginx -s reload nginx: [emerg] unknown directive “错误

重启服务报错 bug: ./nginx -s reload nginx: [emerg] unknown directive "? 原因&#xff1a; 一、可能打开没有关闭 二、刚刚编辑的没成功&#xff0c;乱码了&#xff0c;格式问题&#xff0c;重新配置

汇标网系统搭建,让知识产权保护更智能、更便捷!

据国家商标局统计发布&#xff0c;2023年四季度我国商标申请量达到了6,988,704件&#xff0c;有效商标注册量为44,047,071件&#xff01; 商标作为企业的重要资产&#xff0c;现在不仅企业、个体户、个人等等&#xff0c;都想在商标市场分得一杯羹。 目前&#xff0c;国家和社会…

多模态表征中的里程碑—CLIP及中文版Chinese-CLIP:理论揭秘、代码微调与论文阅读 (视觉与语义的奇妙共舞~)

我之前一直在使用CLIP/Chinese-CLIP&#xff0c;但并未进行过系统的疏导。这次正好可以详细解释一下。相比于CLIP模型&#xff0c;Chinese-CLIP更适合我们的应用和微调&#xff0c;因为原始的CLIP模型只支持英文&#xff0c;对于我们的中文应用来说不够友好。Chinese-CLIP很好地…

【深度学习笔记】深度学习训练技巧

深度学习训练技巧 1 优化器 随机梯度下降及动量 随机梯度下降算法对每批数据 ( X ( i ) , t ( i ) ) (X^{(i)},t^{(i)}) (X(i),t(i)) 进行优化 g ∇ θ J ( θ ; x ( i ) , t ( i ) ) θ θ − η g g\nabla_\theta J(\theta;x^{(i)},t^{(i)})\\ \theta \theta -\eta g g…

leetcode:491.递增子序列

1.误区&#xff1a;不能直接对数组排序再求解子集&#xff0c;因为那样就改变了原有数组的顺序 2.树形结构&#xff1a;一个一个取数&#xff0c;然后保证是递增序列&#xff0c;且不能重复。&#xff08;数层上不可以重复取&#xff0c;树枝上可以重复取&#xff09;收集的结…

[蜥蜴书Chapter2] -- 下载和加载数据

目录 一、下载和加载数据的函数代码 二、代码说明 1、urllib.request.urlretrieve 2、extractall 三、如何调用函数 四、查看数据的结构 1、head函数&#xff1a; 2、info函数&#xff1a; 3、describe函数&#xff1a; 4、绘制柱状图&#xff1a; 一、下载和加载数据…

迁移学习帮大忙!成都理工大学搭建 SCDUNet++ 模型进行滑坡测绘

滑坡是最常见的自然灾害之一&#xff0c;通常由地震和降雨引发&#xff0c;会造成严重的财产损失和人员伤亡。由地震触发的山体滑坡所造成的破坏&#xff0c;有时会比地震本身造成的破坏更为严重。大型地震发生之后&#xff0c;快速、准确地开展滑坡测绘工作 (landslide mappin…

ABAP - Function ALV 05 添加选择框列、全选、取消全选

很多用户不习惯原生GRID的选择模式&#xff0c;所以业务需要用到自定义的选择框来进行数据的操作&#xff0c;显示效果如图所示&#xff0c;增加一条选择列&#xff0c;且配置全选和全选全选的按钮功能&#xff0c;如下图所示。 实现这种功能需要用到Fieldcat的参数控制以及GUI…

18 SpringMVC实战

18 SpringMVC实战 1. 课程介绍2. Spring与Spring MVC环境配置 1. 课程介绍 2. Spring与Spring MVC环境配置

Vue 卸载eslint

卸载依赖 npm uninstall eslint --save 然后 进入package.json中&#xff0c;删除残留信息。 否则在执行卸载后&#xff0c;运行会报错。 之后再起项目。

git之分支管理

一.理解分支 我们看下面这张图片&#xff1a; 在版本回退⾥&#xff0c;你已经知道&#xff0c;每次提交&#xff0c;Git都把它们串成⼀条时间线&#xff0c;这条时间线就可以理解为是⼀个分⽀。截⽌到⽬前&#xff0c;只有⼀条时间线&#xff0c;在Git⾥&#xff0c;这个分⽀…

如何使用Lychee+cpolar搭建本地私人图床并实现远程访问存储图片

文章目录 1.前言2. Lychee网站搭建2.1. Lychee下载和安装2.2 Lychee网页测试2.3 cpolar的安装和注册 3.本地网页发布3.1 Cpolar云端设置3.2 Cpolar本地设置 4.公网访问测试5.结语 1.前言 图床作为图片集中存放的服务网站&#xff0c;可以看做是云存储的一部分&#xff0c;既可…

短链接的背后故事:为互联网用户带来的便捷与安全

title: 短链接的背后故事&#xff1a;为互联网用户带来的便捷与安全 date: 2024/2/26 14:58:58 updated: 2024/2/26 14:58:58 tags: 短链接技术起源长URL问题解决链接分享便利性链接跟踪与分析链接管理效率提升链接安全保障应用领域广泛 一、短链接的起源 短链接是一种将长UR…