贪心算法

一、对贪心算法的理解

贪心算法是通过一系列选择来得到问题的解,并不从整体最优的角度考虑,所做的选择只是在某种意义上的局部最优选择,因此贪心算法并不能解决所有所有的问题。

用贪心算法来解决的问题有两个性质:

1、贪心选择性质:所求问题的整体最优解可以通过一系列局部最优的选择。

2、最优子结构性质:一个问题的最优解包含其子问题的最优解。

与动态规划算法的区别在于,动态规划中每步所做选择依赖于其子问题的解,以自底向上的方式计算,而贪心算法仅作出当前状态下的最优解,再去解决作出这个选择后产生的相应的子问题,以自顶向下的方式计算。

 

二、选择一道作业题目说明你的算法满足贪心选择性质

题目:

货币找零 (30分)
 

人民币的面值有100、50、20、10、5、2、1元。请你输出找零纸币数最少的方案

输入格式:

两个整数,分别表示付款金额和消费金额

输出格式:

输入找零方案。包含若干行,每行包含两个数字,纸币面额和纸币数量

输入样例:

10 3
 

输出样例:

在这里给出相应的输出。例如:

5 1
2 1

代码:
 1 #include <iostream>
 2 using namespace std;
 3 int money[7]={100,50,20,10,5,2,1};
 4 int ans[7]={0};
 5 
 6 int main()
 7 {
 8     int pay, coms;
 9     cin >> pay >> coms;
10     
11     int rest=pay-coms;
12     int i=0;
13     while(rest!=0) {
14         if(rest>=money[i]) {
15             ans[i]=rest/money[i]; 
16             rest =rest-ans[i]*money[i];
17         }
18         i++;
19     }
20     
21     for(int j=0;j<7;j++) {
22         if(ans[j]!=0) { 
23             cout << money[j] << " " << ans[j] << endl;
24         }
25     }
26     
27 }

贪心策略:按面值从大到小选择

证明:

其中一次的选择记为v(i).

若此问题的最优解为S,假设选择v(i)不是最优的,而选择v(j)(j>i),得到最优解S,若用v(i)代替v(j),不会影响后面的选择,仍得到解S,而在假设中,选择v(i)并不是最优的,则产生矛盾,证明贪心策略正确。

 

三、请说明在本章学习过程中遇到的问题及结对编程的情况

1、本章学习过程中遇到的难题:

贪心算法符合现实生活中解决问题的思路,所以理解起来比较容易。但是对于贪心算法的证明还没有掌握,逻辑性太强有点绕。

2、结对编程的情况:

本章结对编程第一道题目比较简单,和同伴都轻松地解决。但是第二道题目的问题太大了,以为只要定义一个结构体,用一个变量记录原先的相对位置,再将几个数排序,然后删掉最大的数,再按原来的位置输出就好了,最后发现只过了测试点,害,原来是没有理解透题目的意思。

觉得本次结对编程的情况并不理想,效率不高,没有办法共同找到问题所在。继续加油!

 

 



posted @ 2020-11-14 11:42  陈雪佩  阅读(171)  评论(0编辑  收藏  举报