当前位置: 首页 > article >正文

【算法笔记】贪心算法

一、什么是贪心算法?

贪心算法是一种在每一步选择中都采取当前看起来最优(最“贪心”)的策略,从而希望得到全局最优解的算法设计思想。

  • 核心思想:每一步都做出局部最优选择,不回退。
  • 适用场景:问题具有最优子结构且满足贪心选择性质 —— 即局部最优可以导出全局最优。

二、贪心算法的典型流程

  1. 排序/预处理:对待选元素进行必要的排序或组织。
  2. 局部选择:按照某种规则(如最大收益、最小代价等)依次选取元素。
  3. 可行性检验:检查当前选择是否满足约束。
  4. 解的构造:在每次选择的基础上逐步构建最终解。

三、经典例题回顾

1. 活动选择问题

  • 题目:有 n n n 个活动,每个活动有开始时间 s i s_i si 和结束时间 f i f_i fi,要求选出最多互不冲突的活动集合。
  • 贪心策略:按活动结束时间从小到大排序,每次选取结束最早且与当前已选活动不冲突的活动。

2. 分数背包问题(Fractional Knapsack)

  • 题目:有 n n n 件物品,每件物品重量 w i w_i wi,价值 v i v_i vi,背包容量 W W W。物品可分割装入。
  • 贪心策略:按单位重量价值 v i w i \frac{v_i}{w_i} wivi 从大到小装入;装不下时装入尽可能多的部分。

3. 最小生成树(Kruskal 算法)

  • 题目:给定带权无向图,求一棵权值之和最小的生成树。
  • 贪心策略:对所有边按权值从小到大排序,依次加入不会形成环的最小边。

四、实战题目 —— 给 n n n 个国家加税

4.1 题目描述

  • n n n 个国家,初始关税税率均为 100%。
  • 对第 i i i 个国家,加税一次可将其税率提升 p i % p_i\% pi%(即税率从上一次的值再加上 p i p_i pi 百分点)。
  • 允许一共进行 k k k 次加税操作,每次只能选择一个国家进行一次加税。
  • 求经过 k k k 次加税后,所有国家税率的累乘(乘积)的最大值。

示例

输入:n = 3, p = [2, 5, 3], k = 4  
输出:最大乘积(按百分比计算)

4.2 贪心思路分析

收益定义
  • 对第 i i i 个国家当前税率 t i t_i ti(最开始 t i = 100 % t_i=100\% ti=100%)再加一次 p i % p_i\% pi%,其新的税率为 t i + p i t_i + p_i ti+pi
  • 在乘积中,相当于将当前乘积乘以 t i + p i t i \frac{t_i + p_i}{t_i} titi+pi,因此这次操作对总乘积的放大倍数为:

r i = t i + p i t i = 1 + p i t i r_i = \frac{t_i + p_i}{t_i} = 1 + \frac{p_i}{t_i} ri=titi+pi=1+tipi

  • 要使乘积最大,每次都应选择能带来最大放大倍数 r i r_i ri 的国家。
优先队列实现
  • 使用一个最大堆(priority_queue)存储每个国家当前可获得的放大倍数 r i r_i ri
  • 每次取出堆顶( r i r_i ri 最大的国家),实施一次加税:
    1. 更新该国家税率: t i ← t i + p i t_i \leftarrow t_i + p_i titi+pi
    2. 计算新的放大倍数: r i ← 1 + p i t i r_i \leftarrow 1 + \frac{p_i}{t_i} ri1+tipi
    3. 将更新后的 r i r_i ri 重新压入堆中。
  • 重复上述过程 k k k 次,结束后遍历所有国家税率,计算乘积。

4.3 代码示例(C++)

#include <bits/stdc++.h>
using namespace std;int main() {ios::sync_with_stdio(false);cin.tie(nullptr);int n, k;cin >> n >> k;vector<double> p(n), t(n, 100.0);for (int i = 0; i < n; i++) {cin >> p[i];}// 优先队列:pair<放大倍数, 国家索引>auto cmp = [](const pair<double,int>& a, const pair<double,int>& b) {return a.first < b.first;};priority_queue<pair<double,int>, vector<pair<double,int>>, decltype(cmp)> pq(cmp);// 初始化for (int i = 0; i < n; i++) {double r = 1.0 + p[i] / t[i];pq.push({r, i});}// 执行 k 次加税while (k--) {auto [r, i] = pq.top(); pq.pop();t[i] += p[i];r = 1.0 + p[i] / t[i];pq.push({r, i});}// 计算累乘结果double ans = 1.0;for (double tax : t) {ans *= tax / 100.0;}cout << fixed << setprecision(6) << ans << "\n";return 0;
}

4.4 复杂度分析

  • 每次操作:弹出堆顶 + 插入堆顶,各 O ( log ⁡ n ) O(\log n) O(logn)
  • 总共 k k k 次操作,时间复杂度为: O ( k log ⁡ n ) O(k \log n) O(klogn)
  • 空间复杂度:需要存储 n n n 个国家的信息,为 O ( n ) O(n) O(n)

五、更多贪心练习题推荐

  1. 区间染色问题:给定区间集合,最少使用多少种颜色使重叠区间不同色?
  2. 跳跃游戏 II:每格有最大跳跃长度,求最少跳跃次数到达末尾。
  3. 分配饼干:孩子有满足度,饼干有大小,如何让最多孩子满足?
  4. 连通区间合并:给一堆区间,合并所有重叠区间,输出不重叠区间集合。

六、小结

  • 贪心算法以“当前最优选择”逐步构建解,适合于“最优子结构”且满足“贪心选择性质”的问题。
  • 真正的难点在于如何证明局部最优能导出全局最优,以及如何设计合适的贪心策略
  • 通过上述“加税”题,以及经典例题的练习,可以加深对贪心算法的理解与应用。

相关文章:

【算法笔记】贪心算法

一、什么是贪心算法&#xff1f; 贪心算法是一种在每一步选择中都采取当前看起来最优&#xff08;最“贪心”&#xff09;的策略&#xff0c;从而希望得到全局最优解的算法设计思想。 核心思想&#xff1a;每一步都做出局部最优选择&#xff0c;不回退。适用场景&#xff1a;…...

Node.js 开发项目

初始化 npm init## npm install 编辑packege.json 添加&#xff0c;以支持ES6的语法 "type": "module" 连接mysql示例 import db from ./db/ops_mysql.jsconst createTable async () > {const insert_data CREATE TABLE IF NOT EXISTS users (…...

网络准入控制系统推荐:2025年构建企业网络安全的第一道防线

随着信息技术的飞速发展&#xff0c;企业网络环境日益复杂&#xff0c;阳途网络准入控制系统作为一种先进的网络安全解决方案&#xff0c;其核心是确保网络接入的安全性。 一、网络准入控制系统的基本原理与功能 网络准入控制以“只有合法的用户、安全的终端才可以接入网络”为…...

XSS跨站--订单和Shell箱子后门

本文主要内容 手法 XSS平台使用 XSS工具使用 XSS结合其他漏洞 XSS具体使用场景 某订单系统XSS盲打_平台 某Shell箱子系统XSS盲打_工具 [1]订单系统经典案例 第一个简易攻击流程&#xff08;订单系统&#xff09;&#xff1a;通过平台完成XSS跨站之后&a…...

游戏遭遇DDoS攻击如何快速止损?实战防御策略与应急响应指南

是不是很抽象 我自己画的 一、游戏DDoS攻击特征深度解析 游戏行业DDoS攻击呈现复合型特征&#xff0c;2023年监测数据显示&#xff0c;针对游戏服务器的攻击中&#xff0c;63%采用UDP反射放大HTTP慢速攻击组合&#xff0c;攻击峰值达3.2Tbps。攻击者利用游戏协议特性&#xff…...

cocos creator使用jenkins打包流程,打包webmobile

windows电脑使用 如果你的电脑作为打包机&#xff0c;一定要锁定自己的ip,如果ip动态获取&#xff0c;可能后续会导致jenkins无法访问,还需要重新配置jenkins和http-server的端口 从jenkins官网下载windows版 Thank you for downloading Windows Stable installer 1.jenkins安…...

自动驾驶(ADAS)领域常用数据集介绍

1. KITTI 数据集 简介&#xff1a;由德国卡尔斯鲁厄理工学院与丰田研究院联合创建&#xff0c;是自动驾驶领域最经典的评测基准&#xff0c;涵盖立体视觉、光流、3D检测等任务。包含市区、乡村和高速公路场景的真实数据&#xff0c;标注对象包括车辆、行人等&#xff0c;支持多…...

C++ 部署的性能优化方法

一、使用结构体提前存放常用变量 在编写前后处理函数时&#xff0c;通常会多次用到一些变量&#xff0c;比如模型输入 tensor 的 shape&#xff0c;count 等等&#xff0c;若在每个处理函数中都重复计算一次&#xff0c;会增加部署时的计算量。对于这种情况&#xff0c;可以考…...

关于IDEA的循环依赖问题

bug描述&#xff1a;&#xff08;java: 模块循环不支持注解处理。请确保将循环 [...] 中的所有模块排除在注解处理之外&#xff09; 解决方法&#xff1a;...

如何在idea中写spark程序

在 IntelliJ IDEA 中编写 Spark 程序&#xff0c;可按以下步骤进行&#xff1a; 1. 创建新项目 打开 IntelliJ IDEA&#xff0c;选择File -> New -> Project。在左侧面板选择Maven或者Gradle&#xff08;这里以 Maven 为例&#xff09;&#xff0c;确保Project SDK选择…...

RAG工程-基于LangChain 实现 Advanced RAG(预检索优化)

Advanced RAG 概述 Advanced RAG 被誉为 RAG 的第二范式&#xff0c;它是在 Naive RAG 基础上发展起来的检索增强生成架构&#xff0c;旨在解决 Naive RAG 存在的一些问题&#xff0c;如召回率低、组装 prompt 时的冗余和重复以及灵活性不足等。它重点聚焦在检索增强&#xff0…...

关于常量指针和指向常量的指针

关于指针&#xff0c;对于常量指针和指向常量的指针也是傻傻分不清。看到定义时&#xff0c;不知道是指针不能变&#xff0c;还是指针指向的内容不能变量。 先看形式&#xff1a; const char * A; char * const B; 这两种有什么区别&#xff1f;傻傻分不清。 A这种定义&am…...

《Masked Autoencoders Are Scalable Vision Learners》---CV版的BERT

目录 一、与之前阅读文章的关系&#xff1f; 二、标题&#xff1a;带掩码的自auto编码器是一个可拓展的视觉学习器 三、摘要 四、核心图 五、结果图 六、不同mask比例对比图 七、“Introduction” (He 等, 2021, p. 1) 引言 八、“Related Work” (He 等, 2021, p. 3)相…...

高压直流输电MATLAB/simulink仿真模型+说明文档

1.模型简介 本仿真模型基于MATLAB/Simulink&#xff08;版本MATLAB 2018Ra&#xff09;软件。建议采用matlab2018 Ra及以上版本打开。&#xff08;若需要其他版本可联系代为转换&#xff09; 使用一个传输功率为1000MW&#xff08;500 kV&#xff0c;2 kA&#xff09;直流互连…...

locust压力测试

安装 pip install locust验证是否安装成功 locust -V使用 网上的教程基本上是前几年的&#xff0c;locust已经更新了好几个版本&#xff0c;有点过时了&#xff0c;在此做一个总结 启动 默认是使用浏览器进行设置的 # 使用浏览器 locust -f .\main.py其他参数 Usage: locust […...

python 线程池顺序执行

在Python中&#xff0c;线程池&#xff08;ThreadPoolExecutor&#xff09;默认是并发执行任务的&#xff0c;但若需要实现任务的顺序执行&#xff08;按提交顺序执行或按结果顺序处理&#xff09;&#xff0c;可以通过以下方案实现&#xff1a; 方案一&#xff1a;强制单线程&…...

第十二届蓝桥杯 2021 C/C++组 空间

目录 题目&#xff1a; 题目描述&#xff1a; 题目链接&#xff1a; 思路&#xff1a; 思路详解&#xff1a; 代码&#xff1a; 代码详解&#xff1a; 题目&#xff1a; 题目描述&#xff1a; 题目链接&#xff1a; 空间 - 蓝桥云课 思路&#xff1a; 思路详解&#…...

以太网的mac帧格式

一.以太网的mac帧 帧的要求 1.长度 2.物理层...

前端如何使用Mock模拟数据实现前后端并行开发,提升项目整体效率

1. 安装 Mock.js npm install mockjs --save-dev # 或使用 CDN <script src"https://cdn.bootcdn.net/ajax/libs/Mock.js/1.0.0/mock-min.js"></script>2. 创建 Mock 数据文件 在项目中新建 mock 目录&#xff0c;创建 mock.js 文件&#xff1a; // m…...

【hadoop】HBase shell 操作

1.创建course表 hbase(main):002:0> create course,cf 2.查看HBase所有表 hbase(main):003:0> list 3.查看course表结构 hbase(main):004:0> describe course 4.向course表插入数据 hbase(main):005:0> put course,001,cf:cname,hbase hbase(main):006:0> …...

如何使用 Redis 缓存验证码

目录 &#x1f9e0; Redis 缓存验证码的工作原理 &#x1f9f0; 实现流程 1. 安装 Redis 和 Python 客户端 2. 生成并缓存验证码 示例代码&#xff1a;生成并存储验证码 3. 发送验证码&#xff08;以短信为例&#xff09; 4. 校验验证码 示例代码&#xff1a;校验验证码…...

深度学习---框架流程

核心六步 一、数据准备 二、模型构建 三、模型训练 四、模型验证 五、模型优化 六、模型推理 一、数据准备&#xff1a;深度学习的基石 数据是模型的“燃料”&#xff0c;其质量直接决定模型上限。核心步骤包括&#xff1a; 1. 数据收集与标注 来源&#xff1a;公开数据集…...

业绩回暖、股价承压,三只松鼠赴港上市能否重构价值锚点?

在营收重返百亿俱乐部后&#xff0c;三只松鼠再度向资本市场发起冲击。 4月25日&#xff0c;这家坚果零食巨头正式向港交所递交上市申请书&#xff0c;若成功登陆港股&#xff0c;将成为国内首个实现“AH”双上市的零食品牌。 其赴港背后的支撑力&#xff0c;显然来自近期披露…...

JAVA-StringBuilder使用方法

JAVA-StringBuilder使用方法 常用方法 append(Object obj) 追加内容到末尾 sb.append(" World"); insert(int offset, Object obj) 在指定位置插入内容 sb.insert(5, “Java”); delete(int start, int end) 删除指定范围的字符 sb.delete(0, 5); replace(int start…...

【Python】Matplotlib:立体永生花绘制

本文代码部分实现参考自CSDN博客&#xff1a;https://blog.csdn.net/ak_bingbing/article/details/135852038 一、引言 Matplotlib作为Python生态中最著名的可视化库&#xff0c;其三维绘图功能可以创造出令人惊叹的数学艺术。本文将通过一个独特的参数方程&#xff0c;结合极…...

Unity AI-使用Ollama本地大语言模型运行框架运行本地Deepseek等模型实现聊天对话(一)

一、Ollama介绍 官方网页&#xff1a;Ollama官方网址 中文文档参考&#xff1a;Ollama中文文档 相关教程&#xff1a;Ollama教程 Ollama 是一个开源的工具&#xff0c;旨在简化大型语言模型&#xff08;LLM&#xff09;在本地计算机上的运行和管理。它允许用户无需复杂的配置…...

terraform使用vault动态管多理云账号AK/SK

为了使用 Terraform 和 HashiCorp Vault 动态管理多个云账号的 Access Key (AK) 和 Secret Key (SK)&#xff0c;可以按照以下步骤实现安全、自动化的凭证管理&#xff1a; 一、架构概述 核心组件&#xff1a; Vault&#xff1a;存储或动态生成云账号的 AK/SK&#xff0c;提供…...

SAP /SDF/SMON配置错误会导致HANA OOM以及Disk Full的情况

一般来说&#xff0c;为了保障每日信息收集&#xff0c;每个企业都会配置/SDF/SMON的监控。这样在出现性能问题时&#xff0c;可以通过收集到的snapshot进行分析检查。如果/SDF/SMON在配置时选取了过多的记录项&#xff0c;或者选择了过低的时间间隔[Interval in seconds],那显…...

CMU和苹果公司合作研究机器人长序列操作任务,提出ManipGen

我们今天来介绍一项完成Long-horizon任务的一项新的技术&#xff1a;ManipGen。 什么叫Long-horizon&#xff1f;就是任务比较长。说到底&#xff0c;也是任务比较复杂。 那么这个技术就给我们提供了一个非常好的解决这类问题的思路&#xff0c;同时&#xff0c;也取得了不错的…...

大模型(LLMs)强化学习—— PPO

一、大语言模型RLHF中的PPO主要分哪些步骤&#xff1f; 二、举例描述一下 大语言模型的RLHF&#xff1f; 三、大语言模型RLHF 采样篇 什么是 PPO 中 采样过程&#xff1f;介绍一下 PPO 中 采样策略&#xff1f;PPO 中 采样策略中&#xff0c;如何评估“收益”&#xff1f; …...