當前位置:首頁 » 操作系統 » 骨架化演算法

骨架化演算法

發布時間: 2022-10-20 01:03:24

❶ 女生怎麼判斷自己是大骨架還是小骨架

如上圖所示測量手腕圍,再用身高除於手腕圍 (cm 對 cm),得到的數字比對下表:

大骨架: <9.6

中骨架: 9.6-10.4

小骨架: >10.4

大骨架: <9.9

中骨架: 9.9-10.9

小骨架: >10.9

參考了以上兩個方法後你是否對自己的骨架大小有了個概念呢?

迷思 2: 骨架大會比較重?

這點也是正確的,因人的骨頭佔了總體重的 10-20%,若骨架大理應體重會稍重個 2-4kg,因此也會看起來稍微大隻。

迷思 3: 骨架大會看起來比較胖?

這是錯誤的觀念,骨架大雖然會比較重,但體重其實無法真正的反應出一個人的體態胖瘦,

就好像西方女星,骨架雖然比我們東亞女性大上許多,但身材卻一樣苗條,

所以說想減肥的朋友們,就別再糾結自己的骨架大小及骨頭重量,

只要好好的鍛煉肌肉,減少脂肪,就算體重變化不大,體態上也會慢慢變好看的喲!

看完了小編的分享後是不是對自己骨架大小有點頭緒了呢?

無論骨架大小想減肥都必須從增肌減脂著手,有了正確的觀念好身材就離你不遠了,繼續加油吧!

-THE END-

❷ 什麼樣的圖像可以進行細化

二值的當然不行。

快速zhang並行演算法,很好的一種常用方法
具體細化方法:
滿足下列四個條件的點可以刪除
p3 p2 p9
p4 p1 p8
p5 p6 p7

細化刪除條件為: (1)、2 < Nz(p1) <= 6 Nz為八鄰域中黑點的數目
(2)、Zo(p1)=1,指中心為黑點
(3)、p2*p4*p8=0 or Zo(p1)!=1 避免黑線被打斷
(4)、p2*p4*p6=0 or Zo(p4)!=1

細化演算法的分類:
依據是否使用迭代運算可以分為兩類:第一類是非迭代演算法,一次即產生骨架,如基於距離變換的方法。遊程長度編碼細化等。第二類是迭代演算法,即重復刪除圖像邊緣滿足一定條件的像素,最終得到單像素寬頻骨架。迭代方法依據其檢查像素的方法又可以再分成串列演算法和並行演算法,在串列演算法中,是否刪除像素在每次迭代的執行中是固定順序的,它不僅取決於前次迭代的結果,也取決於本次迭代中已處理過像素點分布情況,而在並行演算法中,像素點刪除與否與像素值圖像中的順序無關,僅取決於前次迭代的結果。在經典細化演算法發展的同時,起源於圖像集合運算的形態學細化演算法也得到了快速的發展。
Hilditch、Pavlidis、Rosenfeld細化演算法:這類演算法則是在程序中直接運算,根據運算結果來判定是否可以刪除點的演算法,差別在於不同演算法的判定條件不同。
其中Hilditch演算法使用於二值圖像,比較普通,是一般的演算法; Pavlidis演算法通過並行和串列混合處理來實現,用位運算進行特定模式的匹配,所得的骨架是8連接的,使用於0-1二值圖像 ;Rosenfeld演算法是一種並行細化演算法,所得的骨架形態是8-連接的,使用於0-1二值圖像 。 後兩種演算法的效果要更好一些,但是處理某些圖像時效果一般,第一種演算法使用性強些。
索引表細化演算法:經過預處理後得到待細化的圖像是0、1二值圖像。像素值為1的是需要細化的部分,像素值為0的是背景區域。基於索引表的演算法就是依據一定的判斷依據,所做出的一張表,然後根據魔鬼要細化的點的八個鄰域的情況查詢,若表中元素是1,若表中元素是1,則刪除該點(改為背景),若是0則保留。因為一個像素的8個鄰域共有256中可能情況,因此,索引表的大小一般為256。

❸ matlab 圖像骨架化問題請教

可以用函數 bwmorph() 來解決,查看一下 bwmorph() 裡面的選項

BW2 = bwmorph(BW1,'remove'); %提取邊緣
BW3 = bwmorph(BW2,'skel',Inf); %骨架化

❹ 168的身高的女生合理的體重是多少

我國正常成年男性的身高與體重的關系(女性的體重相應減少2.5Kg) 單位:Kg
之前有研究稱,腰圍和臀圍的比例是性感的最重要因素。
但是通過深入調查分析,健康專家認為,體重指數是一個評定性感指數的關鍵數字,它比腰圍和臀圍的比例更能靈敏反映女性身材的變化。
腰臀比 = 腰圍/臀圍
男性 > 0.90、女性> 0.80就表明已經存在局部肥胖了,黃金腰臀比例是:維納斯:0.68;瑪麗蓮·夢露:0.66。
一般認為,正常的體重指數為18到25之間,超重的體重指數為25到30之間,肥胖的體重指數為30以上。當這個描述身高和體重比例的體重指數為20.85時,就意味著這位女性的身材最性感。「因此,減肥的女性就一定要注意自己減肥的尺度了。」專家建議說。但是上面這個標准對於男性來說就並不適用了。
研究人員還表示,對於不同國家的人來說這個性感指數略微有一些差別,但沒有本質上的區別。BMI = 體重(公斤)/[身高(米)]2
例如:1個人身高176厘米,體重75公斤,他的BMI=75/(1.76)2 = 24.2。

女子標准體重對照表 附加三圍標准

中國母性美體曲線對照表

身高 胸部 腰部 臀部 大腿 小腿 標准體重kg 美體重kg

150 79.5 55.5 81.0 46.8 28.1 48.0 43.2

151 80.0 55.9 81.5 47.1 28.2 48.5 43.7

152 80.6 56.2 82.1 47.3 28.4 49.0 44.1

153 81.1 56.6 82.6 47.6 28.5 49.5 44.6

154 81.6 57.0 83.2 47.8 28.7 50.0 45.0

155 82.2 57.4 83.7 48.1 28.9 50.5 45.5

156 82.7 57.7 84.2 48.4 29.0 51.0 45.9

157 83.2 58.1 84.8 48.6 29.2 51.5 46.4

158 83.7 58.5 85.3 48.9 29.3 52.0 46.8

159 84.3 58.8 85.9 49.1 29.5 52.5 47.3

160 84.8 59.2 86.4 49.4 29.6 53.0 47.7

161 85.3 59.6 86.9 49.7 29.8 53.5 48.2

162 85.9 59.9 87.5 49.9 30.0 54.0 48.6

163 86.4 60.3 88.0 50.2 30.1 54.5 49.1

164 86.9 60.7 88.6 50.4 30.3 55.0 49.5

165 87.5 61.1 89.1 50.7 30.4 55.5 50.0

166 88.0 61.4 89.6 51.0 30.6 56.0 50.4

167 88.5 61.8 90.2 51.2 30.7 56.5 50.9

168 89.0 62.2 90.7 51.5 30.9 57.0 51.3

169 89.6 62.5 91.3 51.7 31.0 57.5 51.8

170 90.1 62.9 91.8 52.0 31.2 58.0 52.2

171 90.6 63.3 92.3 52.3 31.4 58.5 52.7

172 91.2 63.6 92.9 52.5 31.5 59.0 53.1

173 91.7 64.0 93.4 52.8 31.7 59.5 53.6

174 92.2 64.4 94.0 53.0 31.8 60.0 54.0

175 92.8 64.8 94.5 53.3 32.0 60.5 54.5
很費勁,請採納,謝謝!

❺ grassfire演算法

這個演算法是做圖像處理的抽骨架處理(文後附抽骨架的簡介),目的是求出圖像的骨架,可以想像一片與物體形狀相同的草,沿其外圍各點同時點火。當火勢向內蔓延,向前推進的火線相遇處各點的軌跡就是中軸。

該處理有很多種不同的演算法,從你提供的程序來看,它屬於距離矩陣的演算法。它要求計算對象必須是體表示的模型(對平面來說,就是二維矩陣),通過計算每個體元素到邊界的最小距離來求取模型的脊點、骨架點.

程序中freespace是輸入矩陣,freespaceX和freespaceY是輸入矩陣的寬和高,navi用來保存輸出矩陣(既矩陣每個元素記錄的是該點到達邊界的最小距離。

freespace輸入矩陣中,值-1代表障礙物邊界,值0代表空白空間。

基本演算法:

1.建立一個用矩形邊界包裹freespace的新臨時矩陣tmpNavi。注意,對於邊界節點,其值仍然為-1,而

對於非邊界節點,給予了一個固定增量(freespaceX*freespaceY*d1)。

2.用多重處理演算法處理臨時矩陣tmpNavi,直至tmpNavi穩定下來,不再發生改變。

3.多重處理中的每次處理的演算法:遍歷每個非邊界節點,計算它經由它的8個相鄰節點分別到達邊界的距離值(既到相鄰節點的距離+相鄰節點自身值),取其中最小值作為它自身新值。這樣周而復始,就能得到一個穩定的數值矩陣。

(程序中用了一些優化的手法,但基本的演算法原理就是這樣的)

4.將臨時矩陣tmpNavi的內容拷貝到輸出矩陣navi,並統計其中的骨點值(最大值)到m_maxValue。

希望以上回答對你有幫助。

抽骨架(Skeletonization)

一個與細化有關的運算是抽骨架,也稱為中軸變換(Medialaxistransform)或焚燒草地技術(grass-firetechnigue)。中軸是所有與物體在兩個或更多非鄰接邊界點處相切的圓心的軌跡。但抽骨架很少通過在物體內擬合圓來實現。

概念上,中軸可設想成按如下方式形成。想像一片與物體形狀相同的草,沿其外圍各點同時點火。當火勢向內蔓延,向前推進的火線相遇處各點的軌跡就是中軸。

抽骨架的實現與細化相似,可採用一個兩步有條件腐蝕實現,但是刪除像素的規則略有不同。

下圖將細化與抽骨架進行比較。二者的主要的差別在於抽骨架在拐角處延伸到了邊界,而由細化得到的骨架卻沒有。

上面圖a是細化的效果,下面的圖b是抽骨架的效果。

(左邊是處理一個均勻的矩形區域,右邊是處理一個均勻的圓形區域)

❻ 基於opencv採用C++或java語言選擇一個二值圖像骨架提取演算法實現並對實驗結果進行評價。

這和什麼語言沒關系。如果想用現成的你可以到directory.fsf.org下載gimp,有很多圖像處理工具的源代碼可以使用,包括C,C++和java。

如果純粹是你個人想嘗試一下,那麼這里純粹是演算法的問題。任何圖像都是以矩陣方式存儲的,不論是文件形式和內存形式。處理之前你首先要清楚這個矩陣的大小,尺寸,每個位元組對應為止的像素含義。搞清楚之後,才是演算法操作。我理解你的「骨架提取」就是將點陣圖向量化的過程,簡單的說,就是由點陣轉換為一系列直線,並記錄每段直線的起點和終點,甚至轉換為連續直線、貝澤爾曲線,或者圓弧。這是個非常高級的數學問題,並不是所有的點陣圖都有解,這也是為什麼像手寫筆識別、臉譜識別和車牌識別迄今為止尚有一些誤差,不可能做到100%成功,識別的過程採用了人工神經網路、前饋網路、多層網路等相當水平的數學方法。舉個例子來說,如果你偶爾看到了某個醫生的處方,可能只能勉強認出一部分文字,這就是為什麼說不是所有點陣圖都有解的一個最簡單的解釋。

❼ 如何做人體骨架模型

本文提供一種將骨架動作矢量映射到人體骨架模型的一種方法,通過輸入各個骨骼的當前方向,反饋給骨架模型,這樣就實現了動畫的效果。實驗開發工具是VC6.0在OpenGL平台上開發完成。

閱讀對象:

假定讀者已經熟悉OpenGL編程,就算不熟悉,只要了解基本的旋轉,平移,堆棧操作就好。
假定讀者已經了解基本的c++編程,其中需要了解遞歸的演算法,遞歸的方法請參考一下數據結構吧。

製作過程:

第一步,3D模型准備

這一步驟的目的是提供分解的骨骼模型,它需要導出多個組成身體結構的文件,模型可以不用自己製作,只要到網上找找吧,應該很多,最好是是人體模型,如果用動物的模型也可以,不過需要自己定義映射骨架了,比如圖中的骷髏模型是我從人體動畫軟體poser 5.0找到的。然後使用3d max 將身體的各個部位導出為3ds文件,這個步驟很簡單,也不需要有什麼3d max的基礎。這里有一個小的技巧就是可以選中多個部分作為一個3ds模型導出,比如我需要將左右肩胛骨與脊椎骨肋骨作為同一個部分導出,這樣可以將它命名為身體軀干(body)。這樣我們就准備了各個3ds文件了,分別是:

身體軀干 BODY.3DS
頭部 HEAD.3DS
左臂 LSHOULDER.3DS
右臂 RSHOULDER.3DS
左小臂 LELBOW.3DS
右小臂 RELBOW.3DS
左大腿 LTHIGH.3DS
右大腿 RTHIGH.3DS
左小腿 LFEET.3DS
右小腿 RFEET.3DS

這樣這些組成部分就可以靈活的拼接出一個人體來了。

第二步,定義相關的核心數據結構

為了得到運動的各個身體部分數據信息,我們需要存儲一些運動信息,主要有:
骨骼ID
骨骼關節的當前位置;r_x,r_y,r_z
骨骼之間的關系,例如手臂是軀乾的延伸,而左小臂是左臂的延伸;PID,CID

我們可以通過下圖來了解骨骼之間的結構關系

存放3ds文件位置;file_name_3ds
3ds模型的初始化方向;這個是比較抽象一點的概念,它是指從父節點指向子節點的方向,例如左小臂的初始位置是平放向下,那麼對應的矢量就是 (-0.2,-1,0)

以下是數據結構部分:
class bone
{
public:
int y;
int x;
int r_z; //現實世界z坐標
int r_y;
int r_x;
int rotated_X; //旋轉後的坐標
int rotated_Y;
int is_marked; //是否已經標記
int PID; //父節點
int CID; //子節點,目前針對軸關節和膝蓋有效
float start_arc_x,end_arc_x; //相對父節點的x 左右方向轉動角度限制
float start_arc_y,end_arc_y; //相對父節點的y 上下方向轉動角度限制
float start_arc_z,end_arc_z; //相對父節點的z 前後方向轉動角度限制
double LengthRatio;
char name[80]; //名稱
char file_name_3ds[180]; //3ds文件名稱
int ID;
bone(int ID,char *name,int PID);
virtual ~bone();
float bone_init_x,bone_init_y,bone_init_z; //初始化骨骼的矢量方向,3d max 模型
};

第三步,初始化骨架結構

在定義了bone的結構以後,我們定義一個skeleton類來在第一次初始化時載入這些結構,

obone = bone (2,"head",1); //定義一個bone
strcpy(obone.file_name_3ds,"head.3DS"); //設置它的3ds文件名
obone.bone_init_x = 0; //初始化骨骼的矢量方向
obone.bone_init_y = 1;
obone.bone_init_z = 0;
bonevec.push_back (obone); //放入vector結構,這里用到了STL編程技術中的vector

以下是實現的部分代碼:
skelecton::skelecton()
{
float fy = 0.56f ;
float ftx = 0.19f;
float ffx = 0.08f;
bone obone = bone (1,"neck",0);
bonevec.push_back (obone);

obone = bone (2,"head",1);
strcpy(obone.file_name_3ds,"head.3DS");
obone.bone_init_x = 0;
obone.bone_init_y = 1;
obone.bone_init_z = 0;
bonevec.push_back (obone);

obone = bone (3,"rShoulder",1);
bonevec.push_back (obone);

obone = bone (4,"lShoulder",1);
bonevec.push_back (obone);

obone = bone (5,"rElbow",3);
strcpy(obone.file_name_3ds,"rShoulder.3DS");
obone.bone_init_x = fy;
obone.bone_init_y = -1;
obone.bone_init_z = 0;
obone.CID = 7;
bonevec.push_back (obone);

obone = bone (6,"lElbow",4);
strcpy(obone.file_name_3ds,"lShoulder.3DS");
obone.bone_init_x = -fy;
obone.bone_init_y = -1;
obone.bone_init_z = 0;
obone.CID = 8;
bonevec.push_back (obone);

//.............太長只給出部分的代碼..........................
}

第四步,學習3ds公共的類CLoad3DS,可以用來載入顯示模型

這個類是公用一個類,詳細的類CLoad3DS的介面信息可以到一個open source項目里參考。http://scourge.sourceforge.net
http://scourge.sourceforge.net/api/3ds_8h-source.html
實際上在使用這個類時候,我做了一些修改,加了得到最大頂點的方法。這個在第五步會說明。

我們定義一個OpenGL的類來做模型控制類,負責載入模型,

CLoad3DS* m_3ds;

int OpenGL::Load3DS(int ID, char *filename)
{
if(m_3ds!=NULL) m_3ds->Init(filename,ID);
return 0;
}

然後在顯示時候調用

int OpenGL::show3ds(int ID)
{
m_3ds->show3ds(ID,0,0,0,2);
return 0;
}

第五步,使用遞歸方法分層次載入模型

這里是重點的內容了,讓我們思考一些問題,實現骨骼會隨著輸入的方向而改變方向,需要做那些事情呢?

首先針對一塊骨骼來考慮:

第一,我們需要讓骨骼繞著它的節點旋轉到輸入的方向上

第二,我們需要知道骨骼目前節點的位置,才能旋轉。可是我們知道骨骼會跟著它的父骨骼轉動的,例如左小臂會跟著左臂轉動,當身體轉動時左臂也會跟著身體轉動的,這里看起來像是有一個父子連動的關系,所以當前節點的位置會與它的父骨骼有關,父骨骼轉動的角度,子骨骼也必須轉動,所以這里自然想到了遞歸模型了,至於如何存儲這些轉動過程呢,還好openGL提供了glPushMatrix();glPopMatrix();那麼所有的子骨骼必須包含在父骨骼的glPushMatrix();glPopMatrix();好了,這個變成

//遞歸實現3d現實
int skelecton::Render_skeleton_3D(int ID)
{

glPushMatrix(); //開始記錄堆棧
joint_point = pgl->get_joint_point(ID); //找到節點位置
glTranslatef(joint_point.x,joint_point.y,joint_point.z); //坐標移到節點位置
pgl->rotate_bone (vt1,vt2,vto); //旋轉骨骼到指定的方向
glTranslatef(-joint_point.x,-joint_point.y,-joint_point.z);//坐標移回來
pgl->show3ds(ID); //顯示模型

//遍歷子節點
for (theIterator = bonevec.begin(); theIterator != bonevec.end(); theIterator++)
{
pbone = theIterator;
if((pbone->PID == ID) )
{
Render_skeleton_3D(pbone->ID); //遞歸調用
}
}

glPopMatrix(); //退出記錄堆棧
}

剩下需要解決的問題就是如何找到節點位置。
尋找節點位置,我們看到上面代碼 get_joint_point(ID)就是找到節點了,其實如果不追求高的准確度,我們可以假設每個模型的最高的點即為骨骼的節點,當然這個假設前提是人體模型是正面站立的,手臂自然垂下,這樣可以近似認為每個模型的最高的點即為骨骼的節點,這樣函數就很簡單了,這個方法是修改了Cload3ds類的方法,如下:

Vector3f CLoad3DS::get_joint_point(int j0)
{
CVector3 LastPoint;
Vector3f vect;
LastPoint.y = -1000 ;
if(j0==2) LastPoint.y = 1000 ;//頭部節點朝下

// 遍歷模型中所有的對象
for(int l = 0; l < g_3DModel[j0].numOfObjects; l++)
{
if(g_3DModel[j0].pObject.size() <= 0) break;// 如果對象的大小小於0,則退出
t3DObject *pObject = &g_3DModel[j0].pObject[l];// 獲得當前顯示的對象

for(int j = 0; j < pObject->numOfFaces; j++) // 遍歷所有的面
{
for(int tex = 0; tex < 3; tex++) // 遍歷三角形的所有點
{
int index = pObject->pFaces[j].vertIndex[tex]; // 獲得面對每個點的索引

if(j0==2)
{
if(pObject->pVerts[index].y < LastPoint.y )
LastPoint = pObject->pVerts[index];
}
else
{
if(pObject->pVerts[index].y > LastPoint.y )
LastPoint = pObject->pVerts[index];
}
}
}
}
vect.x = LastPoint.x ;
vect.y = LastPoint.y ;
vect.z = LastPoint.z ;
return vect;
}

比較特殊的是頭部節點是通過脖子連接的,所以它是取最低的點。

現在解決最後的問題了,如何旋轉了,具體來講就是骨骼從原來自然的狀態旋轉到目前的方向,例如手臂從自然垂下變成抬起,垂下和抬起兩個狀態的矢量是不同的方向的,如何旋轉呢? 這里就要用到了空間幾何里的點積和叉積的概念了,簡單來講就是利用點積來求矢量夾角餘弦,利用叉積來求兩個矢量的法向量,如果你忘記了這些概念,可以回去參考一下高等數學書,這個連接也提供了一些資料,可以幫助理解http://www.gameres.com/Articles/Program/Visual/Other/shiliang.htm
然後呢,我們知道了兩個矢量的夾角與它們的法向量,下面的事情就變得簡單了,我們讓骨骼原來的矢量以法向量為旋轉軸,旋轉一定角度,這個角度就是兩個矢量的夾角,這樣問題就解決了,所以這里的代碼如下:

int OpenGL::rotate_bone(Vector3f vVector1, Vector3f vVector2, Vector3f vVectorOrgin)
{
Vector3f vt1 = Vector3f(vVector1.x,vVector1.y,vVector1.z);
Vector3f vt2 = Vector3f(vVector2.x,vVector2.y,vVector2.z);
Vector3f vt4 = vt2-vt1;

double arc12 = AngleBetweenVectors(vVectorOrgin,vt4);
double rarc12 = 180*arc12/pi;
float len= Distance(vt1,vt2);
Vector3f vt3 = Cross(vVectorOrgin,vt4);
glRotatef ((float)rarc12,vt3.x,vt3.y,vt3.z);

return 0;
}

熱點內容
微博視頻高清上傳設置 發布:2025-05-14 16:38:41 瀏覽:548
資料庫圖書管理設計 發布:2025-05-14 16:33:52 瀏覽:376
php開發的網頁 發布:2025-05-14 16:22:03 瀏覽:477
伺服器內存跑滿了怎麼回事 發布:2025-05-14 16:21:16 瀏覽:224
微信qq音樂緩存 發布:2025-05-14 16:16:16 瀏覽:469
c語言回收內存 發布:2025-05-14 16:16:08 瀏覽:144
2021國產安卓頂級旗艦買哪個 發布:2025-05-14 16:15:36 瀏覽:300
linux自學視頻 發布:2025-05-14 16:14:49 瀏覽:256
我的世界伺服器崩了重啟 發布:2025-05-14 16:09:37 瀏覽:45
android深拷貝 發布:2025-05-14 16:09:35 瀏覽:154