问题分析与解题思路
问题描述理解
在超市货物架上有n个格子,每个格子中有一种商品,用字母a到z表示。顾客进入超市后,会依次从第1格到第n格查找自己想要购买的商品。如果顾客在某个格子找到自己想要的商品,他们就购买该商品并离开。如果在途中遇到空格子(即该格子没有商品)或者查找完所有格子还没有找到商品,他们也会离开。
我们的目标是,给定顾客想要购买的商品种类和货架上商品的初始排列顺序,在最优的商品排列下,计算最多能卖出多少件商品。重新调整商品位置的操作只能在顾客到来之前进行,并且商品的位置不能在顾客到来后再改变。
解题思路
为了解决这个问题,我们可以通过以下几个步骤进行优化和求解:
-
统计商品需求和货架上商品的数量:
- 首先,我们需要了解顾客想要购买的每种商品的需求量,以及货架上每种商品的数量。
-
优化商品顺序:
- 为了最大化售出的商品数量,我们可以通过尽量将顾客需求的商品提前放置在货架上,从而确保顾客能够尽早找到并购买商品。
-
计算能够卖出的商品数量:
- 对于每种商品,顾客的需求量和货架上的商品数量都有限制。最多能售出的商品数量是
顾客需求数量与货架上商品数量中的较小值。因此,我们只需要统计每种商品在货架上出现的数量,并计算每种商品能够满足的需求数量。
- 对于每种商品,顾客的需求量和货架上的商品数量都有限制。最多能售出的商品数量是
-
总售出商品数量:
- 对于每种商品,计算它的最大售出数量,然后将所有商品的售出数量相加。
时间复杂度分析
- 统计顾客需求:O(m),其中
m是顾客的商品种类数。 - 统计货架上的商品:O(n),其中
n是货架格子的数量。 - 计算最大售出数量:O(m),因为每种商品需要处理一次。
总体时间复杂度为O(n + m),这是一个线性的复杂度,可以高效地处理输入数据。
代码实现
java
复制代码
import java.util.HashMap;
import java.util.Map;
public class Main {
public static int solution(int n, int m, String s, String c) {
// 统计顾客需求:记录每种商品的需求数量
Map<Character, Integer> customerNeeds = new HashMap<>();
for (char ch : c.toCharArray()) {
customerNeeds.put(ch, customerNeeds.getOrDefault(ch, 0) + 1);
}
// 统计货物架上的商品:记录每种商品的数量
Map<Character, Integer> shelfItems = new HashMap<>();
for (char ch : s.toCharArray()) {
shelfItems.put(ch, shelfItems.getOrDefault(ch, 0) + 1);
}
// 计算售出的商品数量
int sold = 0;
for (Map.Entry<Character, Integer> entry : customerNeeds.entrySet()) {
char item = entry.getKey(); // 顾客需求的商品
int need = entry.getValue(); // 顾客需求的数量
int available = shelfItems.getOrDefault(item, 0); // 货架上该商品的数量
// 售出的商品数为需求和供应的较小值
sold += Math.min(need, available);
}
return sold;
}
public static void main(String[] args) {
// 测试用例
System.out.println(solution(3, 4, "abc", "abcd") == 3); // true
System.out.println(solution(4, 2, "abbc", "bb") == 2); // true
System.out.println(solution(5, 4, "bcdea", "abcd") == 4); // true
}
}
代码说明
-
统计顾客需求:
- 使用
HashMap存储顾客想要购买的商品及其需求数量。例如,顾客想要购买两件b和一件c,那么customerNeeds的内容将是:{'b': 2, 'c': 1}。
- 使用
-
统计货架商品:
- 使用
HashMap存储货架上每种商品的数量。例如,货架上有一件a,两件b,一件c,那么shelfItems的内容将是:{'a': 1, 'b': 2, 'c': 1}。
- 使用
-
计算最大售出商品数量:
- 遍历顾客需求中的每个商品,检查它在货架上的数量,并将该商品能售出的最大数量加到
sold中。对于每个商品,最多能够售出的数量为Math.min(need, available),即取顾客需求与货架商品数量的较小值。
- 遍历顾客需求中的每个商品,检查它在货架上的数量,并将该商品能售出的最大数量加到
-
返回结果:
- 最终返回售出的商品总数
sold。
- 最终返回售出的商品总数
测试样例
-
输入:
n = 3, m = 4, s = "abc", c = "abcd"- 输出:
3 - 解析:顾客需要
a, b, c, d,货架上有a, b, c,可以出售3件商品。
- 输出:
-
输入:
n = 4, m = 2, s = "abbc", c = "bb"- 输出:
2 - 解析:顾客需要两件
b,货架上有两件b,可以出售2件商品。
- 输出:
-
输入:
n = 5, m = 4, s = "bcdea", c = "abcd"- 输出:
4 - 解析:顾客需要
a, b, c, d,货架上有这些商品的所有要求,最大可售出4件商品。
- 输出:
总结
这道题的关键是理解如何通过最优排列商品使得顾客能够尽可能多地买到他们想要的商品。通过统计顾客的需求和货架上的商品数量,然后计算每种商品能售出的最大数量,我们可以得到最终的结果。这种方法是高效的,时间复杂度为O(n + m),适用于大规模的数据。