【数据结构】贪心算法

一.贪心算法的定义

        贪心算法是指在对问题求解时,总是做出在当前看来是最好的选择。也就是说,不从整体最优上加以考虑,只做出在某种意义上的局部最优解

        贪心算法的结果是最优解的最好近似。

优点:简单,高效。

缺点:可能不是正确的或最优的解

二.引例

当一个问题具有最优子结构性质时,可以用动态规划求解。也可以用贪心算法来求解。

哈夫曼编码:每次选择集合中权值最小的两个子树构成一棵树。

思想:贪心选择思想。

三.贪心算法的基本步骤与实现

1.建立数学模型来描述问题;

2.把求解的问题分成若干个子问题;

3.对每一个子问题求解,得到子问题的局部最优解;

4.把子问题的局部最优解合成原来问题的解。

四.贪心算法的应用

1.活动安排问题

(1)问题描述

1)有n个活动;

2)活动j在$s_j$时刻开始,$f_j$时刻结束;

3)如果两个活动不重叠,则这两个活动是可以兼容的;

4)目标:找到相互兼容的最大活动子集

(2)活动相容性:

设有n个活动的集合E={1,2,……,n},其中,每个活动都要求使用同一资源,如会场等。

而在同一时间内,只有一个活动能够使用该资源。

每个活动i都有一个要求使用该资源的起始时间$s_i$和一个结束时间$f_i$,且$s_i$<$f_i$

如果选择了活动i,则它在半开时间区间[$s_i$,$f_i$)内占用资源。

若区间[$s_i$,$f_i$)与区间[$s_j$,$f_j$)不相交,则称活动i与活动j相容。

(3)贪心策略:

先安排结束时间最早的活动,可以使得剩余的时间极大化,从而安排更多的活动。

(4)伪代码:

1.将所有活动按照结束时间从小到大排列;

2.扫描所有活动的开始时间与结束时间,若扫描到活动i的开始时间早于最近安排的活动j的结束时间,则不安排活动i,否则,安排活动i。

(5)代码:

int greedySelector(int s[],int f[],bool a[],int n){//n代表事件个数,bool类型的数组a表示活动i是否被安排//各活动的起始时间和结束时间存储于数组s和f中且按结束时间的非减序排序int i=0,j=0,count=0;//i表示处理的第i个活动,j表示刚刚安排的活动,count记录安排活动的数量//初始化a[i]=true;//安排第一个事件j=0;count++;for(i=1;i<n;i++){if(s[i]>f[j]) {a[i]=true;j = i;count++;}else{a[i]=false;}}return count;
}

 

(6)其他贪心策略:

1)最早开始时间

按照开始时间$s_i$非递减排序

2)最早结束时间 

按照结束时间$s_i$非递减排序

3)最短间隔

按照间隔长度$f_i-s_i$非递减排序

4)最小冲突

对于每个活动,计算该活动的冲突活动数$c_j$,并按照$c_j$非递减排序

(7)证明贪心算法对于活动安排问题的求解是整体最优解:

对于活动安排问题来说:

最优解即为:使得相容集合的规模最大

数学归纳法进行证明)

证明:

设E={1,2,……,n}活动集合(集合有序)

且按照活动安排结束时间递增排序,即:活动1具有最早的完成时间

假设:活动安排中有一个包含贪心选择的最优解

设A$\subseteq$E是该问题的一个最优解,且集合A也有序,对于A中的活动,将其表示为{$k_1,k_2,...,k_j$},则有活动的开始时间集合S={$s[k_1],s[k_2],...s[k_j]$},以及结束时间集合F=$\{f[k_1],f[k-2],...,f[k_j]\}$

找到一个集合A,首先:A是问题最优解;其次,A是贪心选择出来的集合。

当k=1时,A即为所求。

当k!=1时,设$B=$$A-\{k_1\}\cup\{1\}=\{1,k_2,k_3,...,k_j\}$

由于,$f[1]\leqslant f[k]$,将集合A更改之后,整个集合仍然相容,元素个数也没有改变,集合B也是最优解。

同理,以及将A中的元素替换,由于贪心选择的原理,每次选择结束时间最早的事件,则替换之后,集合仍然是相容的,将所有元素均替换为贪心选择的元素,则集合既是贪心选择的结果,也是最优解,即:贪心选择出的集合是最优解,得证。#

五.贪心算法的基本要素

1.贪心选择性质

所求问题的整体最优解可以通过一系列局部最优的选择达到。

用数学归纳法证明,通过每步的贪心选择,最终可以得到问题的整体最优解。

2.最优子结构性质

当一个问题的最优解包含其子问题的最优解,称此问题具有最优子结构性质。

问题的最优子结构性质是该问题可以用动态规划算法或者贪心算法求解的关键特征。

3.贪心算法和动态规划差别

动态规划:自底向上

贪心算法:从开始逐次迭代

0-1背包问题:

问题描述:

给定n种物品和一个背包。物品i的重量是$w_i $,其价值为$v_i$,背包的容量为C。应如何选择装入背包的物品,使得装入背包中物品的总价值最大。

背包问题:

问题描述:

与0-1背包问题类似,所不同的是,在选择物品i装入背包时,可以选择物品的一部分,而不一定要全部装入背包中。

这两类问题都具有最优子结构性质,但是背包问题可以用贪心算法求解,而0-1背包问题却不能用贪心算法求解。

用贪心算法求解背包问题的基本步骤:

1.计算每种物品单位重量的价值$\frac{v_i}{w_i}$;

2.依据贪心选择策略,将尽可能多的单位重量价值最高的物品装入背包; 

3.若将这种物品全部装入背包后,背包内的物品总重量未超过C,则选择单位重量价值次高的物品并尽可能多地装入背包;

4.依照此策略一直进行下去,直到背包装满为止。

代码实现:

#include <iostream>
using namespace std;struct node{float weight;float value;int number;
};int greedySelector(int s[],int f[],bool a[],int n);
float knapsack(float c,int n,float v[],float w[],float x[]);
int partition(struct node a[],int first,int end);
void quickSort(struct node a[],int first,int end);int main() {int n=5;float v[]={10,40,20,30,25};float w[]={15,12,8,9,10};float x[5];float c=21.5;knapsack(c,n,v,w,x);for(int i=0;i<n;i++){cout<<x[i]<<" ";}cout<<endl;return 0;
}int greedySelector(int s[],int f[],bool a[],int n){//n代表事件个数,bool类型的数组a表示活动i是否被安排//各活动的起始时间和结束时间存储于数组s和f中且按结束时间的非减序排序int i=0,j=0,count=0;//i表示处理的第i个活动,j表示刚刚安排的活动,count记录安排活动的数量//初始化a[i]=true;//安排第一个事件j=0;count++;for(i=1;i<n;i++){if(s[i]>f[j]) {a[i]=true;j = i;count++;}else{a[i]=false;}}return count;
}float knapsack(float c,int n,float v[],float w[],float x[]){//函数的返回值表示总价值//c表示背包容量//n表示物品个数//数组v表示价值value,数组w表示重量weight,数组x表示每个物品放入背包的比例struct node *p=new struct node[n];int i,j;float sum=0;for(i=0;i<n;i++){p[i].number=i;p[i].value=v[i];p[i].weight=w[i];x[i]=0;}quickSort(p,0,n-1);for(i=0;i<n;i++){if(p[i].weight>c){break;}else{x[p[i].number]=1;sum+=p[i].value;c-=p[i].weight;}}if(i<n){x[p[i].number]=c/p[i].weight;sum+=p[i].value*c/p[i].weight;}delete []p;return sum;
}int partition(struct node a[],int first,int end){int i=first,j=end;struct node temp;while(i<j){while(i<j&&(a[j].value/a[j].weight)<=(a[i].value/a[i].weight)){--j;}if(i<j){temp=a[i];a[i]=a[j];a[j]=temp;}while(i<j&&(a[j].value/a[j].weight)<=(a[i].value/a[i].weight)){++i;}if(i<j){temp=a[i];a[i]=a[j];a[j]=temp;}}return i;//i==j时,返回轴值
}void quickSort(struct node a[],int first,int end){if(first<end){int pos=partition(a,first,end);quickSort(a, first, pos-1);quickSort(a, pos+1, end);}
}

贪心算法不适用于0-1背包问题:

对于0-1背包问题,贪心算法得不到最优解。

无法保证最终能够将背包装满,部分闲置的背包空间使得单位重量的价值变低了。

在考虑0-1背包问题时,应比较选择该物品和不选择该物品所导致的最终方案,然后再做出最好选择。由此导出了许多相互重叠的子问题,这正是利用动态规划求解的重要特征。

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/218954.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

关于 python 的 if __name__ == ‘__main__‘ 你知道多少?

在诸多情况下&#xff0c;当我们在编写一个Python测试脚本或是Java转型而来的程序员们&#xff0c;往往偏爱撰写 if name __main__ 的语句。然而&#xff0c;对于 if name __main__&#xff0c;我们究竟了解多少呢&#xff1f; 首先&#xff0c;这是一条判断语句&#xff0c…

百岁时代即将来临,原知因成为消费新潮流

什么叫长寿时代?泰康保险首席执行官陈东升指出&#xff1a;长寿时代&#xff0c;就是百岁人生即将来临&#xff0c;人人带病长期生存。而在这个时代&#xff0c;人类最大的变化在于“生命尺度的改变”&#xff0c;比如过去20岁是年轻人&#xff0c;40岁中年人&#xff0c;60岁…

哈工大《软件工程专业导论》复习指南

哈工大软件工程专业导论复习指南 文章目录 哈工大软件工程专业导论复习指南前言引言——软件工程专业导论课程引言第一章 软件工程专业初步认知第二章 软件体系结构与生命周期第三章 软件需求工程第四章 软件设计与实现第五章 软件质量与软件工程管理第六章 软件工程教育与职业…

经典综述|88.1分力作!土壤塑料际

柏林-勃兰登堡高级生物多样性研究所在《Nature reviews microbiology》期刊上(IF88.1)发表的“The soil plastisphere”研究论文中&#xff0c;综述了塑料对土壤的潜在影响。对土壤塑料际特性和微生物群落以及这些群落影响过程的阐明仍处于早期阶段&#xff0c;但进展的步伐很快…

charCodeAt() 方法

charCodeAt() 是 JavaScript 中用于获取字符串指定位置字符的 Unicode 编码的方法 语法如下&#xff1a; str.charCodeAt(index) str&#xff1a;要获取字符的字符串。index&#xff1a;要获取的字符在字符串中的索引。返回值是一个表示给定索引处字符 Unicode 编码的整数。…

【数据库】@Transactional用法详解

先看代码&#xff0c;你觉得运行结果是什么&#xff1f; public class TestService {Autowiredprivate TestService service;Transactionalpublic void test31() {// 正常代码InfOrdersmesIn in InfOrdersmesIn.builder().zbguid(SnowflakeIdWorker.getSnowflakeId()).zernam…

提升测试工具开发的思考

本文针对测试部效率提升测试工具开发、管理、维护暴露出来的问题的一些思考以及一些个人改进观点。 写在前面 本文提到的效率提升测试工具不是指的部门中固有的自动化测试工具&#xff0c;这里提到的测试工具统一指测试人员在工作之余自主开发用于期望替代重复、繁琐、耗时的手…

数据库_mongoDB

1 介绍 MongoDB 是一种 NoSQL 数据库&#xff0c;它将每个数据存储为一个文档&#xff0c;这里的文档类似于 JSON/BSON 对象&#xff0c;具体数据结构由键值&#xff08;key/value&#xff09;对组成。字段值可以包含其他文档&#xff0c;数组及文档数组。其数据结构非常松散&…

Redis 数据结构:高频面试题及解析

概述 Redis 是速度非常快的非关系型&#xff08;NoSQL&#xff09;内存键值数据库&#xff0c;可以存储键和五种不同类型的值之间的映射。 键的类型只能为字符串&#xff0c;值支持五种数据类型&#xff1a;字符串、列表、集合、散列表、有序集合。 Redis 支持很多特性&…

Nature 确认:大语言模型只是没有感情的「学人精」

DeepMind、EleutherAI 科学家提出&#xff0c;大模型只是在角色扮演。 ChatGPT 爆火后&#xff0c;大语言模型一跃而至&#xff0c;成为了行业与资本的宠儿。而在人们或是猎奇、或是探究地一次次对话中&#xff0c;大语言模型所表现出的过度拟人化也引起了越来越多的关注。 其实…

【DEBUG】AttributeError: module ‘numpy‘ has no attribute ‘object‘

error File “numpy/init.py”, line 305, in getattr AttributeError: module ‘numpy’ has no attribute ‘object’. np.object was a deprecated alias for the builtin object. To avoid this error in existing code, use object by itself. Doing this will not modif…

【数据结构】哈希经典应用:布隆过滤器(哈希+位图)——[深度解析](9)

前言 大家好吖&#xff0c;欢迎来到 YY 滴 数据结构 系列 &#xff0c;热烈欢迎&#xff01; 本章主要内容面向接触过C的老铁 主要内容含&#xff1a; 欢迎订阅 YY滴 数据结构 专栏&#xff01;更多干货持续更新&#xff01;以下是传送门&#xff01; 目录 一.布隆过滤器产生的…

第31期 | GPTSecurity周报

GPTSecurity是一个涵盖了前沿学术研究和实践经验分享的社区&#xff0c;集成了生成预训练Transformer&#xff08;GPT&#xff09;、人工智能生成内容&#xff08;AIGC&#xff09;以及大型语言模型&#xff08;LLM&#xff09;等安全领域应用的知识。在这里&#xff0c;您可以…

Plasmocin® Treatment (ant-mpt)可用于干细胞支原体污染清除

Plasmocin™作为Invivogen的支原体抗生素产品之一&#xff0c;受国内外许多科研工作者使用并大力推广。其包含大环内酯物及对苯二酚两种主要成分&#xff0c;可有效作用于支原体复制的蛋白合成阶段和DNA复制阶段&#xff0c;只需两周即可清除支原体污染&#xff0c;并且不会影响…

【CANoe】CANoe手动发送XCP报文读取观测量

文章目录 1、硬件连接&#xff1a;配置CANoe的CAN端口&#xff0c;连接到ECU标定对应的CAN口2、配置CAN IG模块报文&#xff1a;连接XCP&#xff0c;读取观测量&#xff0c;断开XCP3、报文解析4、参考资料 1、硬件连接&#xff1a;配置CANoe的CAN端口&#xff0c;连接到ECU标定…

文本生成图片 学习笔记

目录 diffusion-v1-5 修改参数sample_size: diffusion-v1-5 安装: pip install diffusers 模型下载地址: 深入浅出完整解析Stable Diffusion(SD)核心基础知识 - 知乎 from diffusers import StableDiffusionPipeline import torchmodel_id = "./stable-diffus…

构筑安全之城:迅软DSE助力大型建筑企业打造数据防泄密方案

电子文件如今已成为各大建筑机构和设计院进行信息存储的主要方式&#xff0c;以及信息交换的重要载体。而对于如何保护好单位内的设计图纸、工程方案等重要资料的数据防泄密问题&#xff0c;就需要相关单位规划好一套合规有效的数据防泄密解决方案。 企业简介 该企业是我国最早…

压缩pdf怎么压缩又小又清晰?超级实用!

当PDF文件过大时&#xff0c;很容易遇到无法上传等现象&#xff0c;这时候我们可以借助一些专业的压缩工具&#xff0c;将PDF文件压缩变小&#xff0c;如果你还不知道怎么做&#xff0c;下面就来看下具体的压缩方法吧。 方法一&#xff1a;使用嗨格式压缩大师 1、打开电脑上安…

Leetcode 78 子集

题意理解&#xff1a; 求一个集合的所有子集。该集合中没有重复元素。 首先明确什么是子集&#xff1a;子集中的元素都在全集里。 [1,2,3] 子集&#xff1a;[]、[1]、[2]、[3]、[12]、[13]、[23]、[123] 注意&#xff1a;[]空集是所有集合的子集。 解题思路&#xff1a; 类似于…

【obs】官方最强插件obs-websocket入门

▒ 目录 ▒ &#x1f6eb; 导读需求开发环境 1️⃣ obs-websocket简介OBS版本说明obs-websocket版本说明安装&#xff08;27.x版本OBS&#xff09;配置插件 2️⃣ OBS-web介绍特征使用方法-5.xhttp vs https 3️⃣ obs-websocket-js开发tester.html 4️⃣ 其它开源项目obs-stud…