各位题友大家好,今天是每日算法题公众号坚持日更的第 8 天。今天力扣上的每日一题是第 839 题「839. 相似字符串组」。可以通过每日一题的小程序查看题目详情:
题目大意
Alice 和 Bob 两个人手里拥有的糖果🍬分别用 A
和 B
表示, A[i]
和 B[i]
分别表示 Alice 和 Bob 两个人手中的糖果的大小。
因为他们是好朋友,所以就想通过交换一个糖果的方式,使得每个人拥有糖果的总大小相等。求两者需要交换的糖果大小,用 res = [a, b]
表示。其中 a 是 Alice 需要交换的糖果大小,b 是 Bob 需要交换的糖果的大小。
示例
输入:A = [1,2], B = [2,3]
输出:[1,2]
解释:Alice 拿出大小为 1 的糖果,与 Bob 拿出的大小为 2 的糖果进行交换。交换后,两者的糖果分别是 A = [2, 2], B = [1, 3]。糖果的大小之和都为 4.
数据范围
1 <= A.length <= 10000
1 <= B.length <= 10000
解题思路
今天的题目是个 Easy 题目,看了数据范围小于等于 10000, 就不要想太多了,可以直接上 O(N) 的解法!
当两个小朋友交换完了糖果🍬之后,两人手中的糖果大小总和就相等了。那这个数字是多少呢?很显然是两个小朋友目前手中糖果的平均数。
所以,我们可以先求出最终两者手中的糖果大小之和是多少,设为 target
。然后逐个判断 Alice 的糖果 A[i]
,计算如果把该糖果交换出去,Bob 应该给 Alice 多大的糖果呢?答案应该是 target - (Alice的糖果总和 - A[i])
,即 Alice 期望的糖果大小之和 target,减去 Alice 剩余的糖果大小之和。
那么问题来了:如果 Alice 想要用 A[i]
跟 Bob 交换,那么 Bob 手里面有没有 Alice 此时想要的糖果大小呢?即 target - (Alice的糖果总和 - A[i])
是否在数组 B 中?
由于遍历 Alice 的糖果需要 O(N) 时间复杂度,此时留给 Bob 查找手里是否有 Alice 想要的这个糖果的时间复杂度只剩 O(1) 了。因为如果也用 O(N) 的时间复杂度查找出来,那么总时间复杂度是 O(N ^ 2)
,数组长度是 10000, 导致总计算量到达 10 ^ 8
,可能会超时。
在常用的数据结构中,只有 Set 能够满足在 O(1) 时间内,判断一个元素是否存在。我们使用 Set 在 Bob 手中查找是否包含目标糖果。
代码
本题的代码比较简单。
- 求数组 A、数组 B 所有糖果大小的总和;使用 set 保存 B 中的各个元素;
- 求出两个小朋友手中糖果大小总和相等时的目标 target;
- 遍历 A 中的每个糖果,求如果把该糖果交换出去,期望 Bob 交换的糖果大小 expect_b。
- 从 B 的 set 中查找是否包含 expect_b,如果包含则说明
[a, expect_b]
是一种可以满足要求的交换。
时间复杂度:O(N),因为只对数组 A 遍历了一次。
空间复杂度:O(N),因为用了 set 保存数组 B 的所有元素。
使用 Python2 写的代码如下。
class Solution(object):
def fairCandySwap(self, A, B):
"""
:type A: List[int]
:type B: List[int]
:rtype: List[int]
"""
sum_A, sum_B, set_B = sum(A), sum(B), set(B)
target = (sum_A + sum_B) // 2
for a in A:
expect_b = target - (sum_A - a)
if expect_b in set_B:
return [a, expect_b]
return []
刷题心得
今天这个题虽然简单,但还是有可以积累的新知识的:
- 时间复杂度的估计,要学会根据数据规模,判断应该用什么时间复杂度的算法。
- 根据时间复杂度寻找合适的算法/数据结构,因此需要牢记算法/数据结构的时间复杂度。
- set 是一种拿空间换时间的数据结构,能够在
O(1)
的时间内判断某个元素是否存在其中。
欢迎加入刷题群
目前已经近 2000 人加入了每日一题打卡群。加入方式是通过每日一题打卡网站。每天都会同步力扣每日一题,这是个互相帮助、互相监督的算法题打卡网站,其地址是 https://www.ojeveryday.com/
想加入千人刷题群的朋友,可以复制上面的链接到浏览器,然后在左侧点击「加入组织」,提交力扣个人主页,即可进入刷题群。期待你早日加入。
关于作者
我是本文的作者是负雪明烛,毕业于北京邮电大学,目前就职于阿里巴巴。坚持刷算法题 5 年,共计刷了 800 多道算法题。做过的每个算法题都在 CSDN 上写题解博客,获得好评无数,CSDN 的累计阅读量已经 160万 次!博客地址是:https://blog.csdn.net/fuxuemingzhu
「每日算法题」公众号是我维护的一个算法题解公众号,主要讲解算法题的解法,也会分享找工作的经验。欢迎关注。
题目来源:839. 相似字符串组https://leetcode-cn.com/problems/similar-string-groups/