贪心算法——五大常用算法之一

本文介绍了贪心算法的基本概念,强调了贪心策略的选择必须具备无后效性。通过经典例题如哈夫曼树构造、背包问题等,阐述了贪心算法的基本思路和适用范围,并提醒在使用贪心策略时需谨慎判断是否能得出全局最优解。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

贪心算法

一、基本概念:

    在对问题求解时,总是做出在当前看来是最好的选择不从整体最优上加以考虑,所做出的仅是在某种意义上的局部最优解

    贪心算法没有固定的算法框架,算法设计的关键是贪心策略的选择。必须注意的是,贪心算法不是对所有问题都能得到整体最优解,选择的贪心策略必须具备无后效性,即某个状态以后的过程不会影响以前的状态,只与当前状态有关。

所以对所采用的贪心策略一定要仔细分析其是否满足无后效性

二、经典例题

可以通过几个例子看一下什么是贪心算法,这个是比较好理解的一个算法。

1、哈夫曼树构造价值问题。

2、不完全(可拆分)背包问题

3、海岸雷达问题

4、普通字符串变换成回文字符串问题

三、贪心算法的基本思路:

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

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

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

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

四、贪心算法适用的问题

    贪心策略适用的前提是:局部最优策略能导致产生全局最优解。实际上,贪心算法适用的情况很少。一般,对一个问题分析是否适用于贪心算法,可以先选择该问题下的几个实际数据进行分析,就可做出判断。

五、贪心策略的选择

     因为用贪心算法只能通过解局部最优解的策略来达到全局最优解,因此,一定要注意判断问题是否适合采用贪心算法策略,找到的解是否一定是问题的最优解。



<think>好的,我需要帮用户理解贪心算法在装船问题中的应用和实现。首先,我得回忆装船问题的基本概念,以及贪心算法的原理。装船问题要求在不超过货船最大载重量的情况下,选择货物使得总价值最大。贪心算法在这里的应用通常是基于某种局部最优的选择,比如价重比。 根据用户提供的引用,问题描述是选择若干货物,使得总重量不超过M,而总价重比最大。这里的价重比指的是每单位重量的价值,即p_i/w_i。所以,贪心策略应该是优先选择价重比高的货物,直到载重量用完。 接下来,我需要整理实现步骤。首先计算每种货物的价重比,然后按照这个比例从高到低排序。排序后依次选取货物,直到无法再装下更多的货物。这里需要注意,可能需要部分装载某一种货物,但根据引用中的输入描述,p_i是w_i的整数倍,可能意味着每种货物可以分割,或者必须整件装载?需要仔细看问题要求。 查看引用[4],输入描述中提到p_i是w_i的整数倍,这可能意味着货物可以按整数倍分割,比如如果选择部分重量,价值也按比例计算。但问题输出是整数,所以可能需要全部装载或者不装,但根据价重比的计算方式,可能允许部分装载。不过,根据代码示例中的做法,用户提供的引用[1]提到使用冒泡排序按价重比排序,然后选择货物直到载重用完,可能这里的货物是可以分割的,即可以取部分重量,这样总价值就是按照价重比计算的。比如,如果剩余载重不足以装下全部某货物,就装部分,此时价值为剩余载重乘以价重比。 然后,实现步骤包括计算价重比、排序、贪心选择。代码中的排序部分引用[1]指出冒泡排序效率低,建议改用快速排序,但装船问题中货物种类固定为10种,所以冒泡排序可能足够,但作为一般情况可能需要更高效的算法。 用户可能想知道具体的实现代码,但根据问题中的引用,代码示例中的结构可能涉及结构体存储货物信息,计算价重比,排序,然后遍历。例如,定义一个货物结构体,包含p、w、c(价重比),然后排序,再累加。 需要注意的问题包括排序的正确性,如何处理剩余载重,以及是否允许部分装载。根据引用中的问题描述,输出是最大价值,而输入中的p_i是w_i的整数倍,可能允许部分装载,但需要确认。例如,若货物A有w=2吨,p=4,价重比2。如果剩余载重为1吨,那么可以装0.5个货物A,得到价值1吨×2=2。但根据输入p_i是w_i的整数倍,这样分割后价值可能还是整数。 在代码实现中,引用[1]提到使用冒泡排序,但可以优化为快速排序。因此,在示例代码中,可能使用快速排序来提高效率,尤其是当货物种类较多时。 总结回答的结构应该是:问题描述、贪心策略(按价重比排序)、实现步骤、代码示例、优化建议、应用场景,以及潜在问题和注意事项。同时,生成相关问题,如与其他算法对比、时间复杂度和处理不可分割货物的情况等。 需要确保所有数学公式用$...$,比如价重比表示为$c_i = \frac{p_i}{w_i}$,独立公式用$$...$$。例如,总价值的计算公式可能需要单独成段。 最后,根据引用中的信息,正确添加引用标记,如引用[1]提到使用冒泡排序,可以将其放在对应段落末尾。同时,确保回答使用中文,代码语法正确,结构清晰。</think>### 贪心算法在装船问题中的实现与应用 #### 一、问题描述 装船问题要求从$N$种货物中挑选若干吨装入货轮,**总重量不超过$M$吨**,且**总价值最大化**。引用中明确说明,货物可分割(因$p_i$是$w_i$的整数倍),因此允许选择部分货物[^4]。 #### 二、贪心策略设计 贪心算法的核心是**价重比优先**,即优先选择$\text{价重比} = \frac{\text{价值}}{\text{重量}}$最高的货物。这一策略的数学表示为: $$c_i = \frac{p_i}{w_i}$$ 通过按$c_i$降序排序,逐步装载直至载重$M$耗尽[^1]。 #### 三、实现步骤 1. **计算价重比**:遍历所有货物,计算$c_i = p_i / w_i$ 2. **排序**:按$c_i$从高到低对货物排序(冒泡排序或更优算法) 3. **贪心选择**:依次装载货物,若当前货物重量$\leq$剩余载重,则全装;否则装部分[^3] #### 四、代码实现(Python) ```python def load_ship(M, goods): # 计算价重比并排序 sorted_goods = sorted(goods, key=lambda x: x[0]/x[1], reverse=True) total_value = 0 remaining = M for p, w in sorted_goods: if remaining >= w: total_value += p remaining -= w else: total_value += (p / w) * remaining break # 载重已满 return int(total_value) # 因p_i是w_i整数倍,结果必为整数 # 示例输入:M=100, goods格式为[(p1, w1), (p2, w2), ...] print(load_ship(100, [(60, 10), (120, 30), (100, 20)])) # 输出:240 ``` #### 五、优化与注意事项 1. **排序效率**:当$N$较大时,冒泡排序$O(n^2)$效率低,可改用快速排序$O(n \log n)$[^1] 2. **输入约束**:$p_i$是$w_i$的整数倍,确保部分装载时价值仍为整数 3. **空间优化**:无需存储完整结构体,直接使用元组排序 #### 六、应用场景 1. 物流运输中的**集装箱装载优化** 2. 资源分配问题(如云计算资源调度) 3. 背包问题的简化版本(可分割物品)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值