leetcode刷题记录

Posted by xnchen on July 7, 2021

标志注释

* :不会

? :有点疑惑

√ :过了

每日一题

序号题目 类型 解法思路 算法复杂度 结果
1711. 大餐计数 双指针、哈希表 1. 数组内数大小在[min, max]范围内,则满足条件的2的幂次在[min, 2max]中,这个复杂度为logC
2. 如果直接去找所有组合可能为2的幂次的数量,复杂度是O(n^2
logC)以上。应该首先将所有数出现的次数存到Dict中。(可以先sort,使顺序从小到大)。然后左右flag去查相加为某个2幂次的数(两数之和)(复杂度为N),进行logC次。
O(NlogC) *

GO

题目序号 类型 解法思路 时间复杂度 空间复杂度 结果
1. 两数之和 哈希表 1. go的字典写法:goDict := make(map[int]int)
或者goDict := map[int] int{}
2. go的查询字典中键值是否存在的写法:if _, ok := goDict[key]; ok {}
3. go遍历list的写法:for index, number := range nums {}
O(logN) O(logN)
剑指 Offer 56 - I. 数组中数字出现的次数 位操作 1. go的转换二进制字符串方法:fmt.Sprintf("%08b", number)或者strconv.FormatInt(number, 2)
2. go的异或:a^b
3. go的字符转数字:rune(c),数字转字符串:string(num)
O(logN) O(1)
1832. 判断句子是否为全字母句   1. go创建固定长度列表的方法:var l[26] int
更新:这样在长度是var的时候会报错,请用l=make([]int, length)
2. go快速判断元素是否在数组中:使用sort.SearchSrtings() 可将判断元素在数组中的问题降低复杂度到O(logN)
   
1833. 雪糕的最大数量 哈希表 方法1:先排序,再计算,复杂度=排序的O(NlogN)
go的列表排序方法:sort.Ints(targetList)
方法2:因为雪糕的最大价格不超过1e5,使用列表记录每个价格的雪糕的数量。空间复杂度换时间复杂度。
O(N+C),C是雪糕最大价格 O(C)
1722. 执行交换操作后的最小汉明距离 并查集、哈希表 1. 分析题目,如果[0,1],[1,2]可以交换,那么[0,2]也可以交换。因此所有可以交换的索引可以形成一个集合,其中两两可以交换
2. 使用并查集得到交换操作的集合
3. 对于每一个集合,使用哈希表记录集合内索引对应的目标数组数据出现的次数。对于输入数组的每一个数,找出其索引所在集合和目标数组集合的差集,就是结果。
O(N+M)
N为集合长度,M为交换列表长度
  *
930. 和相同的二元子数组 哈希表法、三指针法 1. 哈希表法:用哈希表存储hash[sum](从最左侧到index i的累计为sum的数量),在index i,查找hash[sum-goal],即为以index i为右边界的子数组数量。时间、空间复杂度都为O(N)
2. 三指针法:左指针left1、left2,右指针right。其中右指针不断右移,左指针中,left1停在子数组sum>=goal时(连续0的右侧),left2停在sum>goal时(连续0的左侧)。然后就能通过left1和2的索引值差得到以右指针为右边界的子数组数量。时间复杂度O(N),空间复杂度O(1)
    *
面试题 17.10. 主要元素 Boyer-Moore 投票算法 1. 初始状态,candidate任意值,count=0。
2. 遍历输入数组nums中所有元素。当count=0时,使candidate=nums[i]。否则,当candidate!=nums[i],count-=1,当candidate==nums[i],count+=1。
3. 如果数组中存在主要元素,当遍历结束,candidate即为该主要元素。否则,candidate可能为任意值。因此需要再一次遍历数组,确认该数字是否为主要元素。
O(N) O(1) *
91. 解码方法 dp string转int:n, err := strconv.Atoi(string) O(N) O(1)
1818. 绝对差值和 二分查找 sort 1. go中的二分查找:j := nums.Search(v) nums是已经排序好的数列 O(NlogN) O(N)  
1653. 使字符串平衡的最少删除次数 dp 1. go中的空语句(类似python中的pass)直接空着就可以{}
2. string类型也可以使用for循环迭代,中间的元素应该是char?
O(N) O(1)
1105. 填充书架 dp   O(N^2) O(N)
1838. 最高频元素的频数 排序 滑动窗口 1. 先调用一个排序
2. 然后使用滑动窗口
O(NlogN) O(logN)
138. 复制带随机指针的链表 递归 哈希表 1. go的全局变量需要在函数的外部声明:var hashMap map[*Node]*Node,然后在函数内赋值:hashMap = map[*Node]*Node {}
2. 创建一个Node类型的对象,然后将对象地址赋给Node类型指针:flag := &Node {Val:0}
3. 这是一个使用递归的题目,对于母链表中的节点node,检查hash表中对应的newnode有没有被创建,有创建则返回该newnode,没有被创建则创建newnode,然后将该newnode更新到hash表中,然后继续检查node的next node和random node指向的节点。
O(N) O(N) *
300. 最长递增子序列 贪心 二分法 1. 目的是找到最小递增幅度
2. 建立一个空序列d,遍历目标数组。当目标数组遍历到的nums[i]>d[-1]时,直接将nums[i]插入d的最后。当nums[i]大于d[-1]时,使用二分法将其替换掉d数组中正好大于nums[i]且小于等于nums[i]的某个数。
3. 最后得到的空序列长度即为最长递增子序列长度(但是d并不是最长递增子序列,是一个工具数组)
O(NlogN) O(N) *
1713. 得到子序列的最少操作次数 哈希表 最长递增子序列 1. 实际上的解法:将arr中的数字转换成其在target中对应的index,寻找该index序列的最长递增子序列
2. 如果直接将arr数字转换成index序列,复杂度为O(NM),超过题目限制。利用题目中arr中数字不重复的特性,加入哈希表Dict,key为arr中数字,value为对应index。然后再遍历target,如果如果target[i]存在于哈希表的键值中,则查找对应value是否加入该递增子序列。
O(M+NlogN) O(N+M) ?
func in(target string, str_array []string) bool {
    sort.Strings(str_array)
    index := sort.SearchStrings(str_array, target)
    if index < len(str_array) && str_array[index] == target {
        return true
    }
    return false
}