使用 Unity Sentis 和 Compute Shader,det 您所在的位置:网站首页 人脸五官位置图片女人 使用 Unity Sentis 和 Compute Shader,det

使用 Unity Sentis 和 Compute Shader,det

2024-07-05 04:21| 来源: 网络整理| 查看: 265

前言

在计算机视觉领域,人脸五官定位是一个重要的任务。本文将介绍如何使用 Unity Sentis 和 Compute Shader,结合 det_10g.onnx 模型,实现高效的人脸五官定位。我们将详细讲解每一步骤,并提供完整的代码示例。

模型分析

输入值:

模型的输入是我这边选择的是1x3x640x640;

输出值:步长8, 16, 32 的三组数据

(448,451,454):这是步长为8的一组数据,448(12800x1=>1x80x80x2 ),步长为8,高宽640,640/8=80,每行80个预测框,共80行。通过insightface的源码可以看到,num_anchors = 2,每个位置的目标框是两组,正常来说是黑白图两种,既然是同一个位置,那么可以合并一起,意思就是有2张图 ,每张图大小是80x80,有这么多分值。

451:bboxs: 1x8x80x80 每一个分数对应的四个点(x1,y1,x2,y2)*注意这个点是距离原点的相对值,还是需要计算的,这里1x8  前面1~4 是一个矩形框的点,后面的4~8是另一张图的矩形框坐标点,就是黑白图。

454:kps:1x20x80x80 每一个分数对应的五官坐标点(x,y)*注意这个点是距离原点的相对值,还是需要计算的,这里1~10 是一组坐标点,另外的10~20是另外一张图的一组坐标点,分开计算就行。

(471,474,477):这是步长为16的一组数据,与上同理。

(494,497,500):这是步长为32的一组数据,与上同理。

代码示例(待优化): using System; using System.Collections.Generic; using Unity.Mathematics; using Unity.Sentis; using UnityEngine; using System.Linq; public class Retinaface :MonoBehaviour { public ModelAsset modelAsset; public Model model; private IWorker worker; private GPUComputeBackend gpu; public int textureWidth=640, textureHeight =640; private int[] feat_stride_fpn = new int[] {8, 16, 32}; public Dictionary center_cache = new Dictionary() ; private int _num_anchors = 2; private FunctionalTensor anchor_centers; private float det_scale = 2.5f; public ComputeShader postprocess1; private RenderTexture scoresRT; private RenderTexture boxesRT; private RenderTexture kpssRT1; private RenderTexture kpssRT2; private RenderTexture kpssRT3; private RenderTexture kpssRT4; private RenderTexture kpssRT5; private ComputeBuffer post1; public ComputeShader postprocess2; private ComputeBuffer post2; private ComputeBuffer counter; private void Start() { InitBuffer(); model = ModelLoader.Load(modelAsset); gpu = new GPUComputeBackend(); var model2 = Functional.Compile(input => { List scores_list = new List(); List bboxes_list = new List(); List kpss_list = new List(); var outputs = model.Forward(input); //遍历不同步长 for (int i = 0; i < feat_stride_fpn.Length; i++) { var scores = outputs[i*3]; var bbox_preds = outputs[i * 3+1]* feat_stride_fpn[i]; var kps_preds = outputs[i*3+2] * feat_stride_fpn[i]; int height = 640 / feat_stride_fpn[i]; int width = 640 / feat_stride_fpn[i]; var key = (height, width, feat_stride_fpn[i]); if (center_cache.ContainsKey(key) ) { anchor_centers = center_cache[key]; } else { //构建坐标系 var range_X = Functional.ARange(0, height); var range_640_x = range_X.Unsqueeze(-1).BroadcastTo(new[] {height}); var range_640_y = range_640_x.Transpose(0, 1); //(n,n,2) anchor_centers =Functional.Stack(new[] {range_640_y, range_640_x}, 2); //(n*n,2) anchor_centers = (anchor_centers * feat_stride_fpn[i]).Reshape(new[] {-1, 2}); //(n*n*2,2) (12800,2)(3200,2)(800,2) anchor_centers = Functional.Concat(new []{anchor_centers,anchor_centers},1).Reshape(new[] {-1, 2}); if (center_cache.Count


【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有