首页 > 其他分享 >chapter7-贪心策略1-简单贪心

chapter7-贪心策略1-简单贪心

时间:2024-03-07 17:12:45浏览次数:43  
标签:arr 策略 int chapter7 cin ++ include 贪心

贪心策略:总是做出当前最好的选择。给你一个大的问题,贪心策略分为三步走:

  • 问题分解成为多个子问题;

  • 子问题求局部最优解;

  • 局部最优解组合成原问题的解。

适用范围:如果这类最优化问题具备无后效性,即某个状态以前的过程不会影响以后的状态,而只与当前状态有关,就能保证使用贪心策略一定能够获得全局最优解。

(or换个说法,目前的问题具有最优子结构,全局最优解就由各个子问题的最优解构成的话,就能用贪心策略。)

1简单贪心

FatMouse' Trade-1009OJ

尽可能多的咖啡豆:贪心策略

注意:商品可任意切分,无需买完

问题分析:
胖老鼠贪心.jpg

胖老鼠-得到最多咖啡豆
//杭电OJ1009-FatMouse' Trade
#include <iostream>
#include <cstdio>
#include <algorithm>

using namespace std;

const int MAXN = 1000;

struct room {
    int JavaBean;
    int CatFood;
};
room r[MAXN];

bool Compare(room a, room b) { //按性价比排序
    return (double)a.JavaBean / a.CatFood > (double)b.JavaBean / b.CatFood;
}

double MaxTrade(int m, int n) {
    double answer = 0;
    for(int i = 0; i < n; ++i) {
        if(m > r[i].CatFood) {
            answer += r[i].JavaBean;
            m -= r[i].CatFood;
        } else {
            double tmp = (double) m / r[i].CatFood * r[i].JavaBean;
            answer += tmp;
            m = 0;
            break;
        }
    }
    return answer;
}

int main()
{
    int m, n;
    while(cin >> m >> n) {
        if(-1 == m && -1 == n) {
            break;
        }
        for(int i = 0; i < n; ++i) {
            cin >> r[i].JavaBean >> r[i].CatFood;
        }
        sort(r, r + n, Compare);
        double answer = MaxTrade(m, n);
        printf("%.3f\n", answer);
    }
}

Senior's Gun-5281OJ

尽可能多的奖金:贪心策略

问题分析:
神枪手贪心.jpg

最强的枪打最弱的怪
//杭电OJ5281-Senior's Gun
#include <iostream>
#include <cstdio>
#include <algorithm>

using namespace std;

const int MAXN = 1e5 + 10;

long long gun[MAXN];
long long monster[MAXN];

bool Compare(long long a, long long b) {
    return a > b;
}

int MaxMoney(int n, int m) {
    int answer = 0;
    for(int i = 0; i < n; ++i) {
        if(gun[i] <= monster[i] || i >= m) { //枪比怪多
            break;
        }
        answer += gun[i] - monster[i];
    }
    return answer;
}

int main()
{
    int t, n, m;
    cin >> t;
    for(int i = 0; i < t; ++i) {
        cin >> n >> m;
        for(int j = 0; j < n; ++j) {
            cin >> gun[j];
        }
        for(int k = 0; k < m; ++k) {
            cin >> monster[k];
        }
        sort(gun, gun + n, Compare);
        sort(monster, monster + m); //升序 
        cout << MaxMoney(n, m) << endl;
    }
    return 0;
}

ECNU 1045. 箱子打包

尽可能少的装箱数:贪心策略

注意条件:每个箱子最多包含两件物品,如果没有这个条件,就变成普通的装箱问题,在多项式时间内无法得到确定的解(NP-hard)。

问题分析:
箱子打包.jpg

箱子打包
//箱子打包 2024-03-05
#include <iostream>
#include <cstdio>
#include <algorithm>

using namespace std;

const int MAXN = 1e5 + 10;
int length[MAXN];

int main()
{
    int n, l;
    cin >> n >> l;
    for(int i = 0; i < n; ++i) {
        cin >> length[i];
    }
    sort(length, length + n);
    int left = 0;
    int right = n - 1;
    int answer = 0;
    while(left <= right) {
        if(length[left] + length[right] > l) {
            right--;
        } else {
            left++;
            right--;
        }
        answer++; //不管怎样,left = right时一样加一个箱子装这个物品
    }
    cout << answer << endl;
}

POJ 2456 Aggressive cows

题目描述:
Farmer John has built a new long barn, with N (2 <= N <= 100,000) stalls. The stalls are located along a straight line at positions x1,...,xN (0 <= xi <= 1,000,000,000). His C (2 <= C <= N) cows don't like this barn layout and become aggressive towards each other once put into a stall. To prevent the cows from hurting each other, FJ want to assign the cows to the stalls, such that the minimum distance between any two of them is as large as possible. What is the largest minimum distance?

输入:

  • Line 1: Two space-separated integers: N and C
  • Lines 2..N+1: Line i+1 contains an integer stall location, xi

输出:

  • Line 1: One integer: the largest minimum distance

样例输入
5 3
1
2
8
4
9
样例输出
3

问题的诉求:最大的最小间距。注意以后在题目中遇到“最大的最小”、或“最小的最大”这种奇怪的问法,多半都是要通过二分策略来进行解决。

二分策略是贪心策略中的一种,此时问题的求解方法要发生一定变化,从最大值问题转化为一个判定性问题。
判定性问题.jpg

冲动的牛
//Aggressive cows 2024-03-07 二分策略 left_most right_most
#include <iostream>
#include <cstdio>
#include <algorithm>

using namespace std;

const int MAXN = 1e5 + 10;
int arr[MAXN]; //用于存放牛棚的坐标位置

//n个牛棚,c头牛,最小距离为distance能否做到
bool Judge(int n, int c, int distance) {
    int current = arr[0];
    int number = 1;
    for(int i = 1; i < n; ++i) {
        if(arr[i] - current >= distance) {
            number++;
            current = arr[i];
        }
        if(number >= c) {
            return true;
        }
    }
    return false;
}


int main()
{
    int n, c;
    while(scanf("%d%d", &n, &c) != EOF) {
        for(int i = 0; i < n; ++i) {
            scanf("%d", &arr[i]);
        }
        sort(arr, arr + n); //升序
        //二分策略
        int left = 1; //min_distance = 1
        int right = arr[n - 1] - arr[0];
        while(left <= right) {
            int middle = left + (right - left) / 2;
            if(Judge(n, c, middle)) {
                left = middle + 1;
            } else {
                right = middle - 1;
            }
        }
        printf("%d\n", right);
    }
    return 0;
}

POJ 3104 Drying

题目描述:
现有n件衣服需要烘干,每件衣服的含水量为ai
如果自然晾干,每分钟含水量减少1
如果使用烘干机烘干,每分钟含水量减少k(直至为0)
只有一台烘干机,每次只能烘干一件衣服,且一次至少使用1分钟
求使所有衣服含水量为0的最少时间是多少

输入:
第一行包含一个数字n(1<= n <= 10^5),表示衣服的数量。第二行有n个数,分别表示各件衣服的含水量ai(1<= ai<= 10^9),第三行一个整数k(1<= ai <= 10^9),表示烘干机一分钟能够减少的含水量。

输出:
输出一个整数,表示烘干衣服所需的最小时间。

样例输入:
3
2 3 9
5

样例输出:
3

题目诉求

最小的烘干时间 : 二分策略

最小值问题 转化为 判定性问题。
烘干衣服.jpg
代码实现时,判定时间time内能否烘干全部衣服,直接整数相除是有问题的,只会取下整,而实际上我们应该取上整,即使含水量为4,烘干能力为5,也要多花一整分钟的时间。

烘干衣服
//POJ 3104 Drying  2024-03-07
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>

using namespace std;

const int MAXN = 1e5 + 10;
int arr[MAXN]; //保存含水量

//n件衣服,在time时间内能否全部烘干
bool Judge(int n, int k, int time) {
    int hong_time = 0;
    for(int i = 0; i < n; ++i) {
        if(arr[i] > time) {
            int num = ceil((arr[i] - time)*1.0 / (k - 1));
            hong_time += num;
        }
        if(hong_time > time) {
            return false;
        }
    }
    return true;
}

int main()
{
    int n, k;
    cin >> n;
    for(int i = 0; i < n; ++i) {
        cin >> arr[i];
    }
    cin >> k;
    sort(arr, arr + n);
    if(k == 1) {
        cout << arr[n-1] << endl;
    }    

    //二分策略
    int left = 1; //min_need_time = 1
    int right = arr[n - 1];
    while(left <= right) {
        int middle = left + (right - left) / 2;
        if(Judge(n, k, middle)) {
            right = middle - 1;
        } else {
            left = middle + 1;
        }
    }
    cout << left << endl;
    return 0;
}

标签:arr,策略,int,chapter7,cin,++,include,贪心
From: https://www.cnblogs.com/paopaotangzu/p/18051493

相关文章

  • win共享盘出现用户名或密码错误,你不能访问此共享文件夹,因为你组织的安全策略阻止未经
     win10共享文件夹的创建、访问凭据一直提示“用户名或密码错误”的解决办法_输入你的凭据以连接到用户名和密码不正确-CSDN博客 https://blog.csdn.net/wxp353/article/details/127055846 如何解决“你不能访问此共享文件夹,因为你组织的安全策略阻止未经身份验证的来宾访......
  • 从CF1935C看带反悔的贪心和multiset
    Problem-C-Codeforces.思路首先很显然对\(b\)数组排序能最小化\(b\)的花费。难点在\(a\)的选择,因为已经对\(b\)排序,不可能再兼顾\(a\)的优劣,所以\(a\)需要类似枚举的技术,这是一个类似搜索最优子集的问题,可以用\(DP\),但是更可以贪心带反悔的贪心这类问题就......
  • 华为交换机配置acl策略
    [SX-12FS-CoreSW]aclnamea19953001[SX-12FS-CoreSW-acl-adv-a1995]dis [SX-12FS-CoreSW-acl-adv-a1995]displaythi [SX-12FS-CoreSW-acl-adv-a1995]displaythisaclnamea19953001rule999permitipsource192.168.195.00.0.0.255destination172.25.82.630......
  • asp.net core 中基于策略的授权-自定义授权
    前两篇文章扫盲篇,进阶篇中介绍了基本的asp.netcore中基于策略的授权的使用方法。使用策略授权时,只能指定策略,不能配置其他信息。[Authorize(Policy="AtLeast21")]//指定要验证的策略publicclassAlcoholPurchaseController:Controller{publicIA......
  • ASP.NET Core策略授权和ABP授权
    首先我们来创建一个WebAPI应用。然后引入Microsoft.AspNetCore.Authentication.JwtBearer包。策略Startup类的ConfigureServices方法中,添加一个策略的形式如下:services.AddAuthorization(options=>{options.AddPolicy("AtLeast21",policy=>......
  • 千卡利用率超98%,详解JuiceFS在权威AI测试中的实现策略
    2023年9月,AI领域的权威基准评测MLPerf推出了 StorageBenchmark。该基准测试通过模拟机器学习I/O负载的方法,在不需要GPU的情况下就能进行大规模的性能压测,用以评估存储系统的在AI模型训练场景的适用性。目前支持两种模型训练:BERT(自然语言模型)和Unet3D(3D医学成像)......
  • Vue源码解读:更新策略
    之前介绍过初始化时Vue对数据的响应式处理是利用了Object.defifineProperty(),通过定义对象属性getter方法拦截对象属性的访问,进行依赖的收集,依赖收集的作用就是在数据变更的时候能通知到相关依赖进行更新。通知更新setter当响应式数据发生变更时,会触发拦截的setter函数......
  • 机器学习策略篇:详解训练/开发/测试集划分(Train/dev/test distributions)
    训练/开发/测试集划分设立训练集,开发集和测试集的方式大大影响了或者团队在建立机器学习应用方面取得进展的速度。同样的团队,即使是大公司里的团队,在设立这些数据集的方式,真的会让团队的进展变慢而不是加快,看看应该如何设立这些数据集,让团队效率最大化。在此,想集中讨论如何设立......
  • 动手学强化学习(五):值迭代与策略迭代代码
    一、策略迭代importcopyclassCliffWalkingEnv:"""悬崖漫步环境"""def__init__(self,ncol=12,nrow=4):self.ncol=ncol#定义网格世界的列self.nrow=nrow#定义网格世界的行#转移矩阵P[state][action]=[(p,next_state,......
  • C++新U4-贪心算法1
    学习目标贪心算法的概念[【贪心算法(一)】书架]    【题意分析】选出最少的奶牛数量,让他们的身高相加超过书架的高度。【思路分析】优先选择身高高的奶牛,这样子奶牛使用的数量最少。定义排序规则,将数从大到小排序定义奶牛数量n和书架高度b,并且输入输......