算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)

这篇具有很好参考价值的文章主要介绍了算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

4-1 会场安排问题

(一)题目

问题描述

假设在足够多的会场里安排一批活动,并希望使用尽可能少的会场。设计一个有效的贪心算法进行安排。(这个问题实际上是著名的图着色问题。若将每个活动作为图的一个顶点,不相容活动间用边相连。使相邻顶点有着不同颜色的最小着色数,相当于要找的最少会场数。)

算法设计

对于给定的 n n n个待安排活动,计算使用最少会场的时间。

数据输入

由文件input.txt提供输入数据。第1行中有一个整数 n n n,表示有 n n n个待安排的活动。接下来的 n n n行中,每行有2个正整数,分别表示 n n n个待安排的活动的开始时间和结束时间。时间以0点开始的分钟计。

结果输出

将计算的最少会场数输出到文件output.txt。

(二)解答

方法思路

会场安排问题可以用贪心算法求解,采用结束时间最早的会场作为贪心选择

算法具体描述:

1)用数组s和f分别存储各活动的开始时间和结束时间,将s按非递减排序,该次序为各活动选择会场的次序;将f按非递减排序, 由于会场的结束时间由活动的结束时间决定,排序后的数组也是会场的结束时间点。

2)先为最早开始的活动开辟一个会场,此时会场的最早结束时间为该活动的结束时间,然后遍历剩下的活动,对于每个活动,判断当前最早结束的会场内是否仍有活动(即会场的最早结束时间大于该活动的开始时间),如果有,开辟一个新会场;如果没有,说明当前最早结束的会场能容纳当前的活动,更新会场的结束时间点,保证最早结束的会场最先开始下一个活动。

算法正确性证明:

1)贪心选择性质的证明

优解包含贪心选择的证明可用反证法,证明如下:

假设最优解不含贪心选择,即最优解 A A A的某个活动 a a a所选择的会场 r ’ r’ r不是结束时间最早的会场 r r r,由于 r r r的结束时间小于 r ’ r’ r a a a能在 r r r中进行,说明 a a a必定能在 r r r中进行,因此用 r r r代替 r ’ r’ r的结果 ( A − { r ′ } ) ∪ { r } (A-\{r'\})\cup\{r\} (A{r}){r} 仍是一个最优解,即最优解包含贪心选择,与假设矛盾。

2)最优子结构性质的证明

A A A是原问题 E E E的最优解,会场 r 1 r_1 r1安排的活动集合为 e e e,则 A ′ = A − { r 1 } A'=A-\{r_1\} A=A{r1}是子问题 E ′ = E − e E'=E-e E=Ee的最优解,该命题的证明可用反证法,证明如下:

假设 B ′ B' B是子问题 E ′ E' E的更优解, B ′ B' B A ′ A' A所需的会场数更少,由于 E ′ E' E e e e不相容,新开辟一个会场 r r r容纳活动集合 e e e B ′ B' B无影响,那么 B ′ ∪ { r } B'\cup\{r\} B{r}是原问题的更优解,与假设矛盾。

综上,会场安排问题可用贪心算法求解,且将结束时间最早的会场为贪心选择能得到最优解。

举例

设有4个活动,每个活动的开始和结束时间分别为{1, 6}, {4, 8}, {9, 10}, {7, 18}
算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)
总共需要2个会场

源代码
#include <cstdio>
#include <iostream>
#include<fstream>
#include <algorithm>

using namespace std;

int main()
{
    int n; //活动个数
    int s[100]; //各活动开始时间
    int f[100]; //各活动结束时间
    int i, j; //i,j分别指向开始时间和结束时间
    int ans; //结果

    //文件输入
    ifstream ifs;
    ifs.open("G:\\algorithm\\data\\4_1_input.txt", ios::in);
    ifs>>n;
    for (int i = 1; i <= n; ++i)
    {
        ifs>>s[i]>>f[i];
    }
    ifs.close();

    //排序
    sort(s + 1, s + n + 1); //将各活动的开始时间按非递减排序,排序后的数组为各活动选择会场的次序
    sort(f + 1, f + n + 1); //将各活动的结束时间按非递减排序,由于会场的结束时间由活动的结束时间决定,排序后的数组也是会场的结束时间点
    
    //为最早开始的活动开辟一个会场,此时会场的最早结束时间为该活动的结束时间
    j = 1;
    ans = 1;
    
    //遍历剩下的活动
    for (int i = 2; i <= n; ++i)
    {
        //判断当前最早结束的会场内是否仍有活动
        //如果有,开辟一个新会场
        if (f[j] > s[i])
        {
            ans++;
        }
        //如果没有,说明当前最早结束的会场能容纳当前的活动,更新会场的结束时间点,保证最早结束的会场最先开始下一个活动
        else
        {
            j++;
        }
    }

    //文件输出
    ofstream ofs;
    ofs.open("G:\\algorithm\\data\\4_1output.txt", ios::out);
    ofs<<ans<<endl;
    ofs.close();
}
结果示例

输入:

算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)

输出:

算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)

(三)总结

复杂度分析:

排序函数sort()的时间复杂度为 O ( n l o g n ) \Omicron(nlogn) O(nlogn)

为除最早结束的活动外的活动选择会场的循环次数为 n − 1 n-1 n1,时间复杂度为 O ( n ) \Omicron(n) O(n)

因此,整个算法的时间复杂度为 O ( n l o g n ) \Omicron(nlogn) O(nlogn)文章来源地址https://www.toymoban.com/news/detail-470326.html

到了这里,关于算法分析与设计-会场安排问题(贪心)(通俗易懂,附源码和图解,含贪心选择性质和最优子结构性质的证明)(c++)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 湘潭大学 算法设计与分析实验 回溯 动态规划 贪心 模拟退火解决背包问题

    https://download.csdn.net/download/SQ_ZengYX/88620871 测试用例

    2024年02月02日
    浏览(62)
  • KMP算法——通俗易懂讲好KMP算法:实例图解分析+详细代码注解 --》你的所有疑惑在本文都能得到解答

    KMP 是一个 解决模式串在文本串是否出现过 ,如果出现过,最早出现的位置的经典算法。 Knuth-Morris-Pratt 字符串查找算法,简称为 “KMP 算法”,常用于 在一个文本串 S 内查找一个模式串 P 的出现位置 ,这个算法由 Donald Knuth 、 Vaughan Pratt 、 James H. Morris 三人于 1977 年联合发表

    2024年02月07日
    浏览(50)
  • 【贪心算法】LeetCode2071:你可以安排的最多任务数目

    [二分查找]LeetCode2040:两个有序数组的第 K 小乘积 二分查找算法合集 给你 n 个任务和 m 个工人。每个任务需要一定的力量值才能完成,需要的力量值保存在下标从 0 开始的整数数组 tasks 中,第 i 个任务需要 tasks[i] 的力量才能完成。每个工人的力量值保存在下标从 0 开始的整数

    2024年02月05日
    浏览(46)
  • 【算法分析与设计】贪心算法(下)

      给定带权有向图G =(V,E),其中 每条边的权是非负实数 。另外,还给定V中的一个顶点,称为源。现在 要计算从源到所有其它各顶点的最短路长度 。 这里路的长度是指路上各边权之和 。 这个问题通常称为单源最短路径问题 。   Dijkstra算法是解单源最短路径问题的贪心

    2024年02月08日
    浏览(41)
  • 算法设计与分析之贪心算法

    贪心算法(Greedy Algorithm)是一种基于贪心思想的算法策略。它通过每一步选择当前状态下最优的解决方案,从而逐步得到全局最优解。贪心算法通常在问题具有 贪心选择性质 和 最优子结构性质 时被应用。 贪心算法的基本思想是,每一步选择当前情况下看起来最好的解决方

    2024年02月11日
    浏览(46)
  • 【算法分析与设计】贪心算法(上)

      理解贪心算法的概念。   掌握贪心算法的基本要素   (1) 最优子结构性质   (2) 贪心选择性质   理解贪心算法与动态规划算法的差异   理解贪心算法的一般理论   通过应用范例学习贪心设计策略。   (1) 活动安排问题 ;   (2) 最优装载问题

    2024年02月08日
    浏览(49)
  • 【四】【算法分析与设计】贪心算法的初见

    假设你是一位很棒的家长,想要给你的孩子们一些小饼干。但是,每个孩子最多只能给一块饼干。 对每个孩子 i ,都有一个胃口值 g[i] ,这是能让孩子们满足胃口的饼干的最小尺寸;并且每块饼干 j ,都有一个尺寸 s[j] 。如果 s[j] = g[i] ,我们可以将这个饼干 j 分配给孩子

    2024年03月17日
    浏览(46)
  • 直接选择排序:最通俗易懂的排序算法

    🎬 鸽芷咕 :个人主页  🔥 个人专栏 : 《数据结构算法》《粉丝福利》 ⛺️生活的理想,就是为了理想的生活! 直接选择选择排序也是八大排序之一的排序算法,虽然实际应用上其实并不会选择它来进行排序,但它的思想和价值还是十分值得我的去学习的! 选择排序的思想

    2024年02月03日
    浏览(36)
  • 机器学习算法:UMAP 深入理解(通俗易懂!)

    UMAP 是 McInnes 等人开发的新算法。与 t-SNE 相比,它具有许多优势,最显着的是提高了计算速度并更好地保留了数据的全局结构。降维是机器学习从业者可视化和理解大型高维数据集的常用方法。最广泛使用的可视化技术之一是 t-SNE,但它的性能受到数据集规模的影响,并且正

    2024年02月16日
    浏览(47)
  • 算法设计与分析实验:动态规划与贪心

    目录 一、零钱兑换 1.1 思路一:动态规划 1.2 思路二:贪心 二、安排工作以达到最大效益 2.1 具体思路 2.2 思路呈现 2.3 代码实现 2.4 复杂度分析 2.5 运行结果 三、雇佣k名工人的最低成本 3.1 具体思路 3.2 思路展示 3.3 代码实现 3.4 复杂度分析 3.5 运行结果 结尾语 “生活有意思的

    2024年02月19日
    浏览(75)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包