??xml version="1.0" encoding="utf-8" standalone="yes"?>国产视频一区二区在线观看 ,蜜桃av一区二区,国产亚洲午夜http://www.shnenglu.com/deane/category/5616.html 前进......zh-cnWed, 13 May 2009 08:06:04 GMTWed, 13 May 2009 08:06:04 GMT60堆排?/title><link>http://www.shnenglu.com/deane/articles/82548.html</link><dc:creator>李阳</dc:creator><author>李阳</author><pubDate>Mon, 11 May 2009 03:57:00 GMT</pubDate><guid>http://www.shnenglu.com/deane/articles/82548.html</guid><wfw:comment>http://www.shnenglu.com/deane/comments/82548.html</wfw:comment><comments>http://www.shnenglu.com/deane/articles/82548.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/deane/comments/commentRss/82548.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/deane/services/trackbacks/82548.html</trackback:ping><description><![CDATA[<p><br>1?堆排序定?br>     n个关键字序列KlQK2Q?#8230;QKnUCؓ堆,当且仅当该序列满_下性质(UCؓ堆性质)Q?br>     (1) ki≤K2i且ki≤K2i+1 ?2)Ki≥K2i且ki≥K2i+1(1≤i≤  )</p> <p>     若将此序列所存储的向量R[1..n]看做是一完全二叉树的存储结构,则堆实质上是满如下性质的完全二叉树Q树中Q一非叶l点的关键字均不大于(或不于)其左叛_?若存?l点的关键字?br>【例】关键字序列(10Q?5Q?6Q?5Q?0Q?0)?70Q?6Q?0Q?5Q?5Q?0)分别满堆性质(1)?2)</p> <p>2、大根堆和小根堆<br>     根结?亦称为堆?的关键字是堆里所有结点关键字中最者的堆称为小根堆?br>     根结?亦称为堆?的关键字是堆里所有结点关键字中最大者,UCؓ大根堆?br>  注意Q?br>     ①堆中Q一子树亦是堆?br>     ②以上讨论的堆实际上是二叉堆(Binary Heap)Q类似地可定义k叉堆?/p> <p>3、堆排序特点<br>     堆排?HeapSort)是一树Ş选择排序?br>     堆排序的特点是:在排序过E中Q将R[l..n]看成是一完全二叉树的顺序存储结构,利用完全二叉树中双亲l点和孩子结点之间的内在关系【参见二叉树的顺序存储结构】,在当前无序区中选择关键字最?或最?的记录?/p> <p>4、堆排序与直接插入排序的区别<br>     直接选择排序中,Z从R[1..n]中选出关键字最的记录Q必进行n-1ơ比较,然后在R[2..n]中选出关键字最的记录Q又需要做n-2?比较。事实上Q后面的n-2ơ比较中Q有许多比较可能在前面的n-1ơ比较中已经做过Q但׃前一排序时未保留这些比较结果,所以后一排序时又重复执 行了q些比较操作?br>     堆排序可通过树Şl构保存部分比较l果Q可减少比较ơ数?/p> <p>5、堆排序<br>    堆排序利用了大根?或小根堆)堆顶记录的关键字最?或最?q一特征Q得在当前无序Z选取最?或最?关键字的记录变得单?/p> <p>Q?Q用大根堆排序的基本思想<br>?先将初始文gR[1..n]建成一个大根堆Q此堆ؓ初始的无序区<br>?再将关键字最大的记录R[1](卛_?和无序区的最后一个记录R[n]交换Q由此得到新的无序区R[1..n-1]和有序区R[n]Q且满R[1..n-1].keys≤R[n].key<br>?׃交换后新的根R[1]可能q反堆性质Q故应将当前无序区R[1..n-1]调整为堆。然后再ơ将R[1..n-1]中关键字最大的记录R[1]和该?间的最后一个记录R[n-1]交换Q由此得到新的无序区R[1..n-2]和有序区R[n-1..n]Q且仍满_pR[1..n-2].keys≤R [n-1..n].keysQ同栯R[1..n-2]调整为堆?br>    ……<br>直到无序区只有一个元素ؓ止?/p> <p>Q?Q大根堆排序法的基本操作:<br>?初始化操作:R[1..n]构造ؓ初始堆;<br>?每一排序的基本操作Q将当前无序区的堆顶记录R[1]和该区间的最后一个记录交换,然后新的无序区调整为堆(亦称重徏??br>  注意Q?br>①只需做n-1排序,选出较大的n-1个关键字卛_以得文仉增有序?br>②用根堆排序与利用大根堆类|只不q其排序l果是递减有序的。堆排序和直接选择排序相反Q在M时刻Q堆排序中无序区L在有序区之前Q且有序区是在原向量的尾部由后往前逐步扩大x个向量ؓ止?/p> <p>Q?Q堆排序的算法:<br>  void HeapSort(SeqIAst R)<br>   { //对R[1..n]q行堆排序,不妨用R[0]做暂存单?br>    int iQ?br>    BuildHeap(R)Q?//R[1-n]建成初始?br>    for(i=n;i>1Qi--){ //对当前无序区R[1..i]q行堆排序,共做n-1?br>      R[0]=R[1]QR[1]=R[i];R[i]=R[0]Q?//堆和堆中最后一个记录交?br>     Heapify(RQ?Qi-1)Q?//R[1..i-1]重新调整为堆Q仅有R[1]可能q反堆性质<br>     } //endfor<br>   } //HeapSort</p> <p>Q?Q?BuildHeap和Heapify函数的实?br> 因ؓ构造初始堆必须使用到调整堆的操作,先讨论Heapify的实现?br>?Heapify函数思想Ҏ<br>  每趟排序开始前R[l..i]是以R[1]为根的堆Q在R[1]与R[i]交换后,新的无序区R[1..i-1]中只有R[1]的值发生了变化Q故除R [1]可能q反堆性质外,其余Ml点为根的子树均是堆。因此,当被调整区间是R[low..high]Ӟ只须调整以R[low]为根的树卛_?br>"{选法"调整?br>  R[low]的左、右子树(若存?均已是堆Q这两棵子树的根R[2low]和R[2low+1]分别是各自子树中关键字最大的l点。若R[low]. key不小于这两个孩子l点的关键字Q则R[low]未违反堆性质Q以R[low]为根的树已是堆,无须调整Q否则必dR[low]和它的两个孩子结?中关键字较大者进行交换,即R[low]与R[large](R[large].key=max(R[2low].keyQR[2low+1]. key))交换。交换后又可能ɾl点R[large]q反堆性质Q同L于该l点的两子?若存?仍然是堆Q故可重复上q的调整q程Q对以R [large]为根的树q行调整。此q程直至当前被调整的l点已满_性质Q或者该l点已是叶子为止。上q过E就象过{子一P把较的关键字逐层{下 去,而将较大的关键字逐层选上来。因此,有h此ҎUCؓ"{选法"?br>    具体的算法【参见教材?/p> <p>②BuildHeap的实?br>  要将初始文gR[l..n]调整Z个大根堆Q就必须它所对应的完全二叉树中以每一l点为根的子树都调整为堆?br>  昄只有一个结点的树是堆,而在完全二叉树中Q所有序?的结炚w是叶子,因此以这些结点ؓ根的子树均已是堆。这P我们只需依次以序号?Q?nbsp; -1Q?#8230;Q?的结点作为根的子树都调整为堆卛_?br>     具体法【参见教材】?/p> <p>5、大堆排序实现</p> <p> </p> <p>void HeapSort ( Elem R[], int n ) ...{<br>// 对记录序列R[1..n]q行堆排序?br>for ( i=n/2; i>0; --i )<br>                    // 把R[1..n]建成大顶?br>   HeapAdjust ( R, i, n );<br>for ( i=n; i>1; --i ) ...{<br>R[1]←→R;          <br>        // 堆记录和当前未经排序子序?br>        // R[1..i]中最后一个记录相互交?br>HeapAdjust(R, 1, i-1);            <br>        // R[1..i-1] 重新调整为大堆<br>}<br>} // HeapSort<br>其中{选的法如下所C。ؓR[s..m]调整?#8220;大顶?#8221;Q算法中“{?#8221;应沿关键字较大的孩子l点向下q行?br>void HeapAdjust (Elem R[], int s, int m) ...{<br>// 已知R[s..m]中记录的关键字除R[s].key?br>// 外均满堆的定义Q本函数调整R[s] 的关<br>// 键字QR[s..m]成ؓ一个大堆Q对其中<br>// 记录的关键字而言Q?br>rc = R[s];<br>for ( j=2*s; j<=m; j*=2 ) ...{// 沿key较大的孩子结点向下筛?br>    if ( j<m && R[j].key<R[j+1].key)  ++j;<br>    if ( rc.key >= R[j].key )  break; // rc应插入在位置s?br>    R[s] = R[j];  s = j;<br>}<br>    R[s] = rc; // 插入<br>} // HeapAdjust </p> <p>6?法分析<br>     堆排序的旉Q主要由建立初始堆和反复重徏堆这两部分的旉开销构成Q它们均是通过调用Heapify实现的?br>     堆排序的最坏时间复杂度为O(nlgn)。堆排序的^均性能较接q于最坏性能?br>     ׃建初始堆所需的比较次数较多,所以堆排序不适宜于记录数较少的文件?br>     堆排序是地排序Q辅助空间ؓO(1)Q?br>     它是不稳定的排序Ҏ?/p> <p> <br></p> <img src ="http://www.shnenglu.com/deane/aggbug/82548.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/deane/" target="_blank">李阳</a> 2009-05-11 11:57 <a href="http://www.shnenglu.com/deane/articles/82548.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>囑Ş包含判定法http://www.shnenglu.com/deane/articles/38111.html李阳李阳Sun, 09 Dec 2007 12:26:00 GMThttp://www.shnenglu.com/deane/articles/38111.htmlhttp://www.shnenglu.com/deane/comments/38111.htmlhttp://www.shnenglu.com/deane/articles/38111.html#Feedback0http://www.shnenglu.com/deane/comments/commentRss/38111.htmlhttp://www.shnenglu.com/deane/services/trackbacks/38111.html  
     在进行图形求交时Q常帔R要判定两个图形间是否有包含关pR如Ҏ否包含在U段、^面区域、三lŞ体中Q线D|否包含在q面区域、三lŞ体中Q等{。许多包含判定问题可转化为点的包含判定问题,如判断线D|否在q面上可以{化ؓ判断其两端点是否在^面上。因此下面主要讨论关于点的包含判定算法?/font>

判断点与U段的包含关p,也就是判断点与线的最短距L否位于容差范围内。造型中常用的U段有三U:

Q?Q直U段Q(2Q圆锥曲U段Q主要是圆弧Q,Q?Q参数曲U(主要是BezierQBh与NURBS曲线Q。点与面的包含判定也cM地分ZU情c下面分别讨论?/font>

1、点与直U段的包含判?/font>

假设点坐标ؓP(x, y, z)Q直U段端点为P1(x1, y1, z1)QP2(x2,y2,z2)Q则点P到线DP1P2的距ȝqx?/font>

d2=(x-x1)2+(y-y1)2+(z-z1)2-[(x2-x1)(x-x1)+(y2-y1)(y-y1)+(z2-z1)(z-z1)]2/[(x2-x1)2+(y2-y1)2+(z2-z1)2]

当d2<a2Ӟ认ؓ点在U段Q或其g长线Q上Q这时还需q一步判断点是否落在直线D늚有效区间内。只要对坐标分量q行比较Q假讄D两端点的x分量不等Q否则所有分量均相等Q那么线D两端点重合Q线D退化ؓ一点)Q那么当x-x1与x-x2反号Ӟ点P在线D늚有效区间内?/font>

2、点与圆锥曲U段的包含判?/font>

以圆弧ؓ例,假设点的坐标?x, y, z)Q圆弧的中心为(x0, y0, z0Q,半径为rQv始角a1Q终止角a2。这些角度都是相对于局部坐标系x轴而言。圆弧所在^面ؓ

    ax+by+cz+d=0

先判断点是否在该q面上,若不在,则点不可能被包含。若在,则通过坐标变换Q把问题转换Cl的问题?/font>

l定中心为(x0, y0Q,半径为rQv始角a1Q终止角a2的圆弧,对^面上一点PQx, yQ,判断P是否在圆弧上Q可分二步进行。第一步判断P是否在圆心ؓQx0, y0Q,半径为r的圆的圆周上Q即下式是否成立Q?/font>

    

W二步判断P是否在有效的圆弧D内?/font>

3、点与参数曲U的包含判定

讄坐标为P(x, y, z)Q参数曲UؓQ(t)=(x(t), y(t), z(t))。点也参数曲U的求交计算包括三个步骤Q?/font>

Q?Q计参数t|使P到Q(t)的距L;

Q?Q判断t是否在有效参数区间内Q通常为[0Q?]Q;

Q?Q判断Q(t)与P的距L否小于a 。若Q?Q,Q?Q步的判断均?#8220;?#8221;Q则点在曲线上;否则点不在曲U上?/font>

W一步应计算tQ得|P-Q(t)|最,

?R(t)=(P-Q(t))(P-Q(t))=|P-Q(t)|2最?/font>

Ҏ微积分知识,在该处R'(t)=0?/font>

Q'(t)[P-Q(t)]=0

用数值方法解出t|再代入曲U参数方E可求出曲线上对应点的坐标。第Q?Q、(3Q步的处理比较简单,不再详述?/font>

4、点与^面区域的包含判定

讄坐标为P(x, y, z)Q^面方Eؓax+by+cz+d=0。则点到q面的距Mؓ

    d=

若d<a Q则认ؓ点在q面上,否则认ؓ点不在^面上。在造型pȝ中,通常使用q面上的有界区域作ؓ形体的表面。在q种情况下,对落在^面上的点q应q一步判别它是否落在有效区域内。若点落在该区域内,则认为点与该面相交,否则不相交。下面以q面区域多边形ؓ例,介绍有关法?/font>

判断q面上一个点是否包含在同q面的一个多边Ş内,有许多种法Q这里仅介绍常用的三U:叉积判断法、夹角之和检验法以及交点计数验法?/font>

Q?Q叉U判断法

假设判断点ؓP0。多边Ş点按顺序排列ؓP1P2…Pn。如?.5.2所C。oVi=Pi-P0, i=1, 2, …, n, Vn+1=V1?/font>

那么QP0在多边Ş内的充要条g是叉UViXVi+1(i=1, 2, …, n)的符L同。叉U判断法仅适用于凸多边形。当多边形ؓҎQ尽点在多边Ş内也不能保证上述叉积W号都相同。这时可采用后面介绍的两U方法?/font>

2_5_2.gif (4875 bytes)

?.5.2 叉积判断?/font>

Q?Q夹角之和检验法

假设某^面上有点P0和多边ŞP1P2P3P4P5Q如?.5.3所C。将点P0分别与Pi相连Q构成向量Vi=P-P0。假设角 PiP0Pi+1=ai。如?img height=45 src="file:///F:/软g开?游戏开?数学/2.5.3包含判定法.files/Image101.gif" width=38>=0Q则点P0在多边Ş之外Q如?.5.3(a)所C。如?img height=45 src="file:///F:/软g开?游戏开?数学/2.5.3包含判定法.files/Image102.gif" width=38>=2πQ则点P0在多边Ş之内Q如?.5.3(b)所C。ai可通过下列公式计算QoSi=Vi? Vi+1, Ci=Vi·Vi+1Q则tg(ai)=Si/CiQ所以ai=arctg(Si/Ci)?/font>

ai的符号即代表角度的方向?/font>

2_5_3.gif (5201 bytes)

?.5.3 夹角之和验法

在多边ŞҎ不太多(<44Q的情况下,可以采用下列q似公式计算ai?/font>

    ?|Si|≤|Ci|

  ?|Si|>|Ci|

其中d=0.0355573为常数。当Σαi≥π

Ӟ可判P0在多边Ş内。当ΣαiQ?#960; Ӟ可判P0在多边Ş外。证明略?/font>

Q?Q交点计数检验法

当多边Ş是凹多边形,甚至q带孔时Q可采用交点计数法判断点是否在多边Ş内。具体做法是Q从判断点作一线xIQ?/font>

求射U与多边形边的交点个数。若个数为奇敎ͼ则点在多边Ş内,否则Q点在多边Ş外?/font>

如图2.5.4所C,线a, c分别与多边Ş交于二点和四点,为偶敎ͼ故判断点AQC在多边Ş外。而射Ub, d与多边Ş交三点和一点,为奇敎ͼ所以BQD在多边Ş内?/font>

当射U穿q多边Ş点Ӟ必须Ҏ对待。如?.5.4所C,线fq顶点,若将交点计数?Q则会错误地判断F在多边Ş外。但是,若规定射U过点Ӟ计数?Q则又会错误地判断点E在多边Ş内。正的Ҏ是,若共享顶点的两边在射U的同一侧,则交点计数加2Q否则加1。按q种ҎQE点计?Q所以在多边形外QF点计CؓQ,所以在多边形内。读者可以自己另取一些点来验证?/font>

2_5_4.gif (3218 bytes)

?.5.4 交点计数?/font>

5、点与二ơ曲?参数曲面的包含判?/font>

假设点坐标ؓP(x0, y0, z0)Q二ơ曲面方EؓQ(x, y, z)=0Q则当|Q(x0, y0, z0)|<? Ӟ认ؓ点在该二ơ曲面上Q在造型pȝ中,通常使用裁剪的二ơ曲面。在q种情况下,q要判断Ҏ否在有效范围内。裁剪的二次曲面通常用有理Bezier或有理Bh的参数空间上的闭合曲U来定义曲面的有效范_故要把点所对应的参数空间的参数坐标计算出来Q再判断该参数坐标是否在参数I间有效区域上?/font>

6、点与三lŞ体的包含判定

判断Ҏ否被三维形体所包含Q可先用前面的方法判断点是否在三lŞ体的表面上,然后判断Ҏ否在形体内部Q其Ҏ因Ş体不同而异。下面以凸多面体Z说明?/font>

讑և多面体某个面的^面方Eؓax+by+cz+d=0Q调整方E系数的W号Q当ax+by+cz+d<0Ӟ?x,y,z)位于该^面两侧中包含该凸多面体的一侧。于是要验一个点是否在凸多面体内部,只要验是否它对凸多面体的每一个面均满以上的不等式即可?/font>



李阳 2007-12-09 20:26 发表评论
]]>
þþþ99ƷƬ| þԾƷ| þ99Ʒþþþþ벥| 99ƷþþƷ| ھƷþþþþþɬ| þþƷ}Ů| þҹҹݺ2022| Ʒպþ| þþþ99оƷ10| ƷۺϾþþþþ97| ɫþ| þþƷһ99| þ޾Ʒ| þþùƷ| Ӱһþҹײ | þþƷ۲ӰԺ| þþƷ99þþ㽶| ղƷþþþþþ| ˾þô߽ۺͼƬ| 99þþƷһ | þŮƵ| ҹƵþþþһ| ݺݾþ| ĻۺϾþ2| ƷþþþùA| þþþAVۿ| þþþþAŷAV| Ʒþþþþ| þһձɫۺϾþ| 91鶹Ʒ91þþ| þþƷƷް| 91Ʒ9lþþþ| պþþþþ| ݺݾƷþþĻ| ޹˾Ʒ91þþ| wwwɫ˾þþƷ| þþƷav鶹С˵| ҹþþƷ| ˾þۺ| ޹Ʒþþ | þòӰ|