贪心算法

算法简介

  • 贪心算法是指:在每一步求解的步骤中,它要求“贪婪”的选择最佳操作,并希望通过一系列的最优选择,能够产生一个问题的(全局的)最优解。
  • 贪心算法每一步必须满足一下条件:
    1、可行的:即它必须满足问题的约束。
    2、局部最优:他是当前步骤中所有可行选择中最佳的局部选择。
    3、不可取消:即选择一旦做出,在算法的后面步骤就不可改变了。

例题

(1) 分发饼干

解题步骤:
a. 对需求因子数组g与饼干大小数组s进行从小到大排序;
b.按照从小到大的顺序使用各饼干尝试是否满足某个孩子,每个饼干只尝试一次。若尝试成功,则换下一个孩子尝试,直到发现没有更多的孩子或者没有更多的饼干,循环结束。

class Solution {
public:
    int findContentChildren(vector<int>& g, vector<int>& s) {
        
        int count = 0;
        
        sort(g.begin(), g.end());
        sort(s.begin(), s.end());
        
        vector<int>::iterator itg = g.begin();
        vector<int>::iterator its = s.begin();
        
        while( (itg != g.end()) && (its != s.end()) )
        {
            if( *itg <= *its )
            {
                count++;
                ++itg;
            }
            ++its;
        }
        
        return count;
    }
};

(2)摆动序列


自动机自动转换
class Solution {
public:
    int wiggleMaxLength(vector<int>& nums) {
        
        if( nums.size() < 2)
        {
            return nums.size();
        }
        
        const static int BEGIN = 0;
        const static int UP = 1;
        const static int DOWN = 2;
        
        int STAT = BEGIN;
        int count = 1;
        
        for(int i=1; i<nums.size(); ++i)
        {
            switch( STAT )
            {
                case BEGIN:
                    if( nums[i] > nums[i-1] )
                    {
                        STAT = UP;
                        ++count;
                    }
                    else if( nums[i] < nums[i-1] )
                    {
                        STAT = DOWN;
                        ++count;
                    }
                    break;
                case UP:
                    if( nums[i] < nums[i-1] )
                    {
                        STAT = DOWN;
                        ++count;
                    }
                    break;
                case DOWN:
                    if( nums[i] > nums[i-1] )
                    {
                        STAT = UP;
                        ++count;
                    }
                    break;
            }
        }
        
        return count;
    }
};

(3)移除K位数字

思想:从高位向低位遍历,如果对应的数字大于下一位数字,则把该位数字去掉,得到数字最小
最暴力的方法:去掉k个数字,即从最高位遍历k次。时间复杂度高。
使用栈存储最终结果或删除工作,从高位向低位遍历num,如果遍历的数字大于栈顶元素,则将该数字push入栈,如果小于栈顶元素,则进行pop弹栈,直到栈为空或不能再删除数据(k==0)或栈顶小于当前元素为止。

class Solution {
public:
    string removeKdigits(string num, int k) {
        vector<int> s;      // 用来存储数字的栈
        string str = "";    // 用来存储返回值的字符串
        
        for(int i=0; i<num.size(); ++i)
        {
            int number = num[i] - '0';      // 字符转整数
            while((s.size() != 0) && (s.back() > number) && (k > 0))    // 栈不为空且栈顶元素大于number且k大于0时,需要弹出栈顶元素
            {
                s.pop_back();
                k--;
            }
            
            if( s.size() != 0 || number != 0)   // 当栈不为空或者number不为0时,入栈
            {
                s.push_back(number);
            }
        }
        
        while( s.size() != 0 && k > 0 )     // 如果栈不为空,且还有数字可以删除,从尾部删除
        {
            s.pop_back();
            k--;
        }
        
        if( s.size() == 0 )
        {
            return "0";
        }
        
        for(int i=0; i<s.size(); ++i)
        {
                str += (s[i] + '0');    // 数字转换为字符串
        }
        
        return str;
    }
};

(4)跳跃游戏

class Solution {
public:
    bool canJump(vector<int>& nums) {
        int max_index = 0;
        int i = 0;
        
        for(; (i<nums.size()) && (i<=max_index); ++i)
        {
            int index = i + nums[i];
            if( index > max_index )
            {
                max_index = index;
            }
        }
        
        
        if( i == nums.size() )
        {
            return true;
        }
        else
        {
            return false;
        }
    }
};
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,491评论 5 459
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 81,856评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 141,745评论 0 319
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,196评论 1 263
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,073评论 4 355
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,112评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,531评论 3 381
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,215评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,485评论 1 290
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,578评论 2 309
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,356评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,215评论 3 312
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,583评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,898评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,174评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,497评论 2 341
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,697评论 2 335

推荐阅读更多精彩内容

  • 贪心算法 当具有最优子结构性质的时候,可以使用动态规划算法也可以使用贪心算法 最优子结构性质、贪心选择性质 虽然贪...
    冰源阅读 1,009评论 0 0
  • 前言 贪心是人类自带的能力,贪心算法是在贪心决策上进行统筹规划的统称。 比如一道常见的算法笔试题----跳一跳: ...
    落影loyinglin阅读 41,543评论 11 84
  • 1、前言 求解最优化问题的算法通常会经历一系列步骤,在每个步骤都会面临多种选择,而许多最优化问题并不需要计算每个选...
    某昆阅读 1,595评论 1 5
  • 2017年5月27号 星期六 天气晴 亲子日记第21天 今天下午放学后,姐弟俩个直接到我工作的...
    张欣悦张京坤妈妈阅读 269评论 0 3
  • “种下梦想,不离不弃。” 梦想是,每个人都能把快乐分享给别人。 很小就意识到,我再强大,也是从别人哪里夺取后再分配...
    jieroarchl阅读 180评论 0 2