3. 无重复字符的最长子串
建立一个哈希表,遍历每个字符,将字符下标存进表里
left代表不重复子字符串的开始节点
right代表遍历索引
function lengthOfLongestSubstring(s: string): number { const lastIndex = new Map<string,number>() let left = 0 let max = 0 for(let right=0;right<s.length;right++){ const cur = s[right] if(lastIndex.has(cur)){ left = Math.max(left,lastIndex.get(cur)+1) } lastIndex.set(cur,right) max = Math.max(max,right-left+1) } return max };146.LRU缓存
map是能记录插入顺序的键值对
.size能获取哈希表的长度
.set(key,value),相同的key,新的值覆盖先前的value
.has(key)判断,key在不在哈希表里
.get(key)获取哈希表中key对应的value值
.keys()获取哈希表的所有键值
.keys().next().value获取哈希表中键的最先插进去的键值
class LRUCache { //定义变量 private contain:Map<number,number> private capacity:number constructor(capacity: number) { this.contain = new Map() this.capacity = capacity } get(key: number): number { //如果存在,删除原来的值,重新插入 if(this.contain.has(key)){ const value = this.contain.get(key)! this.contain.delete(key) this.contain.set(key,value) return value }else{ return -1 } } put(key: number, value: number): void { if(this.contain.has(key)){ this.contain.delete(key) } this.contain.set(key,value) if(this.contain.size>this.capacity){ //找到最先插入的键,删除 const trail = this.contain.keys().next().value this.contain.delete(trail) } } } /** * Your LRUCache object will be instantiated and called as such: * var obj = new LRUCache(capacity) * var param_1 = obj.get(key) * obj.put(key,value) */206.反转链表
1->2->3->4->5-null
结果:null<-1<-2<-3<-4<-5
pre cur
cur.next = pre cur.next指向null
pre和cur各进一步
/** * Definition for singly-linked list. * class ListNode { * val: number * next: ListNode | null * constructor(val?: number, next?: ListNode | null) { * this.val = (val===undefined ? 0 : val) * this.next = (next===undefined ? null : next) * } * } */ function reverseList(head: ListNode | null): ListNode | null { if(!head || head.next===null) return head let pre:ListNode | null = null let cur:ListNode | null = head while(cur){ let next = cur.next cur.next = pre pre = cur cur = next } return pre };25.K个一组翻转链表
先翻转前k个元素,递归翻转剩余的链表
head表示旧链表的头
pre表示新链表的头
cur表示下一组翻转链表的开始节点
/** * Definition for singly-linked list. * class ListNode { * val: number * next: ListNode | null * constructor(val?: number, next?: ListNode | null) { * this.val = (val===undefined ? 0 : val) * this.next = (next===undefined ? null : next) * } * } */ function reverseKGroup(head: ListNode | null, k: number): ListNode | null { if(!head || k<=1) return head let count = 0 let index:ListNode | null = head while(index && count<k){ index = index.next count++ } if(count<k) return head let pre:ListNode | null = null let cur:ListNode | null = head for(let i=0;i<k;i++){ const next = cur.next cur.next = pre pre = cur cur = next } head.next = reverseKGroup(cur,k) return pre };15.三数之和
滑动窗口
1.从小到大排序,
2.如果num[i]>0,证明和>0,不符,直接结束循环。有相同的跳过进入下一次循环
2.i从0开始,最后的索引是倒数第三个;j=i+1;z从最后一个索引开始往前
3.计算当前的和,>0,窗口向左移z--;<0,窗口右移j++
4.相等,符合。判断下一个是不是相同的值,相同跳过,最后z--,j++
function threeSum(nums: number[]): number[][] { nums.sort((a,b)=>a-b) const res:number[][] = [] for(let i=0;i<=nums.length-2;i++){ if(nums[i]>0) break if(i>0 && nums[i]===nums[i-1]) continue let j = i+1 let k = nums.length-1 while(j<k){ const sum = nums[i]+nums[j]+nums[k] if(sum>0){ k-- }else if(sum<0){ j++ }else{ res.push([nums[i],nums[j],nums[k]]) while(j<k && nums[j]===nums[j+1]) j++ while(j<k && nums[k]===nums[k-1]) k-- j++ k-- } } } return res };共勉