算法設計與分析複習——第四章:貪心算法

 

第四章:貪心算法

1,貪心算法的設計思想是什麼,有什麼特點?如果一個問題用貪心算法可以獲得全局最優解,那麼該問題的求解應滿足哪些條件?

答:貪心算法的設計思想是在對問題求解時,總是做出在當前看來是最好的選擇。

它的特點是1)不是從整體考慮——得到的解可能不是全局最優 2)簡單,直接,易理解,效率高。

如使用貪心算法求解問題獲得全局最優解,則問題應滿足

1)貪心選擇性質(與動態規劃的主要區別)

所求問題的整體最優解可以通過一系列局部最優的選擇(即貪心選擇)來達到

2)最優子結構性質(動態規劃算法和貪心算法的共同點)

一個問題的最優解包含其子問題的最優解時。

用貪心法求解的問題應具備兩個特性:

1)最優子結構性質

          問題的最優解包含着子問題的最優解。

2)貪心選擇性質

          局部最優解的選擇整體最優解

2,貪心法與動態規劃法的比較

答:貪心法:當前狀態下,局部最優選擇,然後求解作出此選擇之後的子問題。貪心選擇依賴於以往作出的選擇,但不受將來所作的選擇,既不依賴於子問題的解。

動態規劃法:每步所作的選擇依賴於相關子問題的解,只有在解出相關子問題以後,才能作出選擇。

3,如何證明一個問題具有貪心選擇性質?

答:思路:證明每步貪心選擇à問題的整體最優解。

證明步驟:

1)假設問題有一個整體最優解。

2)修改這個最優解,使其以貪心選擇開始,並且證明修改後的解仍然爲最優解。

3)運用數學歸納法,證明:

    每一步貪心選擇問題的整體最優解。

    因爲作出貪心選擇以後,根據最優子結構性質,原問題轉化爲規模更小的子問題。

例題:

1,設n=8[w1,…w8]=[100, 200, 50, 90, 150, 50, 20, 80]c=400

         解:所考察貨箱的次序爲 :7, 3,  6,  8, 4, 1, 5,  2。貨箱7, 3, 6, 8, 4, 1的總重量爲390個單位且已被裝載, 剩下的裝載能力爲10 ,小於任意貨箱.所以得到解

[x1,...x8]=[ 1, 0, 1, 1,  0, 1, 1, 1]

template < class Type >

void Loading(int x[], Type w[], Type c, int n )

{ int *t = new int [n + 1];

   Sort(w, t, n) ; //按貨箱重量排序/

   for (int i = 1; i < = n; i ++)

         x[i] = 0;

   for (int i = 1;i<= n && w[t[i]] <= c; i++) {

             x[t[i]] = 1;

             c-= w[t[i]];}} //調整剩餘空間/

 

2,

n  例:字符出現頻率與編碼方案

            a       b        c          d         e         f

頻率       45       13       12        16         9        5

定長碼     000     001      010       011        100      101

變長碼1    0      1         00        01         10       11

變長碼2    0      101      100      111         1101     1100

 

 

 

3單源最短路徑

 

 

 

4,最小生成樹

 

Kruskal

Prim

template < class Type >

bool Kruskal(int n, int e, EdgeNode < Type > E[ ], EdgeNode < Type > t[ ] ){

               MinHeap < EdgeNode < Type > > H(1);

               H. Initialize(E, e, e);

               UnionFind U(n);

              int k = 0;

              while (e && k < n- 1) {

                    EdgeNode <int > x;

                    H. DeleteMin(x);

                    e--;

                    int a = U.Find(x.u);

                    int b = U.Eind(x.v);

                    if (a! = b) {

                    t[k ++] = x;

                    U. Union(a, b);

}

}

                    H. Deactivate( )

renturn (k = = n-1);

}

Template<class Type>

Void Prim(int n,Type **c)

{     Type lowcost[maxint];

       int closest[maxint];

       bool s[maxint];

       s[1]=true;

       for(int I=2;I<=n;I++)

       {    lowcost[I]=c[1][I];

                closest[I]=1;

             s[I]=false;

       }

       for(int I=1;I<=n;k++)

       {    Type min=inf;

             int j=1;

             for(int k=2;k<=n;k++)

                 if((lowcost[k]<min)&&(!s[k]))

                {    min=lowcost[k];

                      j=k;      }

            cout<<j<<closet[j]<<endl;

       s[j]=true;

for(int k=2;k<=n;k++)

       if((c[j][k]<lowcost[k]&&(!s[k]))

        {

           lowcost[k]=c[j][k];

           closet[k]=j;

       }

}

}

 

 

5,7個獨立的作業{a, b, c, d, e, f, g},加工時間分別爲{214416653}3臺機器:M1, M2, M3貪心調度結果:加工時間爲17,達到最優。

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章