基于TensorFlow.js的Model之PoseNet解析

基于TensorFlow.js的Model之PoseNet解析

Github地址:https://github.com/tensorflow/tfjs-models/tree/master/posenet
Move Mirror:https://experiments.withgoogle.com/move-mirror
Demo:https://storage.googleapis.com/tfjs-models/demos/posenet/camera.html

一、PoseNet 介紹

PoseNet是一個(gè)基于TensorFlow.js的ML Model,可以在瀏覽器中進(jìn)行實(shí)時(shí)人體姿態(tài)估算(pose estimation )。PoseNet既可估算單個(gè)姿勢,也可估算多個(gè)姿勢。

姿勢估算分兩個(gè)階段進(jìn)行:
1、輸入RGB圖像并通過卷積神經(jīng)網(wǎng)絡(luò)解析。
2、使用單姿勢或多姿勢解碼算法,輸出解碼后的姿勢(decode poses)、姿勢置信度得分(pose confidence scores)、關(guān)鍵點(diǎn)位置(keypoint positions)和關(guān)鍵點(diǎn)置信度得分(keypoint confidence scores)。

關(guān)鍵詞:
關(guān)鍵點(diǎn)(keypoint):在估算人體姿勢的時(shí)候,PoseNet為人體選擇了17個(gè)關(guān)鍵點(diǎn),分別如下圖所示。


keypoint.png

關(guān)鍵點(diǎn)位置(keypoint positions):關(guān)鍵點(diǎn)的x和y的坐標(biāo)值。

二、使用PoseNet

1、導(dǎo)入PoseNet庫

$ npm install @tensorflow-models/posenet

2、加載PoseNet Model

const net = await posenet.load(multiplier);

其中,multiplier是所有卷積運(yùn)算的深度(通道數(shù))的浮點(diǎn)乘數(shù),可選取值為: 1.01、1.0、0.75、0.50。
multiplier的值越大,Model的精確度越高,解析速度越慢。
默認(rèn)情況下,multiplier的值為0.75。 建議0.75用于具有中端/低端GPUS的計(jì)算機(jī)。 對于具有強(qiáng)大GPUS的計(jì)算機(jī),建議multiplier為1.0。 移動(dòng)設(shè)備建議使用0.50架構(gòu)的型號。

3、單人姿勢估算算法

單個(gè)姿態(tài)估算更簡單快速,但要求用例圖像中只有一人。 如果圖像中有多個(gè)人,那么來自兩個(gè)人的關(guān)鍵點(diǎn)可能被估計(jì)為同一個(gè)單一姿勢的一部分。例如,第一個(gè)人的左臂和第2個(gè)人的右膝可能會(huì)混淆。

const net = await posenet.load();
const pose = await net.estimateSinglePose(image, imageScaleFactor, flipHorizontal, outputStride);

參數(shù)解析:
image:輸入的圖像(格式:ImageData | HTMLImageElement | HTMLCanvasElement | HTMLVideoElement)
imageScaleFactor:取值0.2~1.0,默認(rèn)為0.50。圖像的縮放值。值越低,圖像越小,傳輸速度越快。
flipHorizontal :默認(rèn)為false。 當(dāng)需要姿勢水平翻轉(zhuǎn)時(shí),取值為true。
outputStride:取值32、16、8,默認(rèn)為16。通過模型輸入圖像時(shí)輸出的所需跨度。 取值越大,輸出越快,準(zhǔn)確度越低。

返回值:返回pose,結(jié)構(gòu)中包括:姿勢的置信度分?jǐn)?shù)和一個(gè)關(guān)鍵點(diǎn)數(shù)組,數(shù)組中包括每個(gè)關(guān)鍵點(diǎn)的名稱、置信度分?jǐn)?shù)和位置。

{
  "score": 0.32371445304906,
  "keypoints": [
    {
      "position": {
        "y": 76.291801452637,
        "x": 253.36747741699
      },
      "part": "nose",
      "score": 0.99539834260941
    },
    {
      "position": {
        "y": 71.10383605957,
        "x": 253.54365539551
      },
      "part": "leftEye",
      "score": 0.98781454563141
    },
    {
      "position": {
        "y": 71.839515686035,
        "x": 246.00454711914
      },
      "part": "rightEye",
      "score": 0.99528175592422
    },
    {
      "position": {
        "y": 72.848854064941,
        "x": 263.08151245117
      },
      "part": "leftEar",
      "score": 0.84029853343964
    },
    {
      "position": {
        "y": 79.956565856934,
        "x": 234.26812744141
      },
      "part": "rightEar",
      "score": 0.92544466257095
    },
    {
      "position": {
        "y": 98.34538269043,
        "x": 399.64068603516
      },
      "part": "leftShoulder",
      "score": 0.99559044837952
    },
    {
      "position": {
        "y": 95.082359313965,
        "x": 458.21868896484
      },
      "part": "rightShoulder",
      "score": 0.99583911895752
    },
    {
      "position": {
        "y": 94.626205444336,
        "x": 163.94561767578
      },
      "part": "leftElbow",
      "score": 0.9518963098526
    },
    {
      "position": {
        "y": 150.2349395752,
        "x": 245.06030273438
      },
      "part": "rightElbow",
      "score": 0.98052614927292
    },
    {
      "position": {
        "y": 113.9603729248,
        "x": 393.19735717773
      },
      "part": "leftWrist",
      "score": 0.94009721279144
    },
    {
      "position": {
        "y": 186.47859191895,
        "x": 257.98034667969
      },
      "part": "rightWrist",
      "score": 0.98029226064682
    },
    {
      "position": {
        "y": 208.5266418457,
        "x": 284.46710205078
      },
      "part": "leftHip",
      "score": 0.97870296239853
    },
    {
      "position": {
        "y": 209.9910736084,
        "x": 243.31219482422
      },
      "part": "rightHip",
      "score": 0.97424703836441
    },
    {
      "position": {
        "y": 281.61965942383,
        "x": 310.93188476562
      },
      "part": "leftKnee",
      "score": 0.98368924856186
    },
    {
      "position": {
        "y": 282.80120849609,
        "x": 203.81164550781
      },
      "part": "rightKnee",
      "score": 0.96947449445724
    },
    {
      "position": {
        "y": 360.62716674805,
        "x": 292.21047973633
      },
      "part": "leftAnkle",
      "score": 0.8883239030838
    },
    {
      "position": {
        "y": 347.41177368164,
        "x": 203.88229370117
      },
      "part": "rightAnkle",
      "score": 0.8255187869072
    }
  ]
}

3、多人姿勢估算算法

多人姿勢估算可以解碼圖像中的多個(gè)姿勢,它比單個(gè)姿勢算法更復(fù)雜且稍慢。

const net = await posenet.load();
const poses = await net.estimateMultiplePoses(image, imageScaleFactor, flipHorizontal, outputStride, maxPoseDetections, scoreThreshold, nmsRadius);

參數(shù)解析:
image:輸入的圖像(格式:ImageData | HTMLImageElement | HTMLCanvasElement | HTMLVideoElement)
imageScaleFactor:取值0.2~1.0,默認(rèn)為0.50。圖像的縮放值。值越低,圖像越小,傳輸速度越快。
flipHorizontal :默認(rèn)為false。 當(dāng)需要姿勢水平翻轉(zhuǎn)時(shí),取值為true。
outputStride:取值32、16、8,默認(rèn)為16。通過模型輸入圖像時(shí)輸出的所需跨度。 取值越大,輸出越快,準(zhǔn)確度越低。
(以上參數(shù)同單人姿勢估算)
maxPoseDetections(可選):默認(rèn)為5,要檢測的最大姿勢數(shù)。
scoreThreshold(可選):默認(rèn)為0.5,僅返回置信度大于或等于此值的實(shí)例。
nmsRadius(可選):默認(rèn)為20。非極大值抑制,以像素為單位,這個(gè)值控制返回人物之間的最小距離。該值的增加或者減少是過濾不太精確的姿態(tài)的一種方式,但只是在調(diào)整姿態(tài)置信度值不夠好的情況下。

返回值:
多人姿勢估算的返回值為多個(gè)單人姿勢估算返回值的組成的數(shù)組。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容