From 5b3e13210504089b250c865a340c08d37a48524f Mon Sep 17 00:00:00 2001 From: markilue <745518019@qq.com> Date: Wed, 19 Apr 2023 14:17:02 +0800 Subject: [PATCH] =?UTF-8?q?leecode=E6=9B=B4=E6=96=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../hot100/second/T02_2_AddTwoNumbers.java | 81 +++++++++++++++ .../T03_3_LengthOfLongestSubstring.java | 45 +++++++++ .../hot100/second/T26_49_GroupAnagrams.java | 48 +++++++++ .../hot100/second/T27_53_MaxSubArray.java | 61 ++++++++++++ .../leecode/hot100/second/T29_56_Merge.java | 56 +++++++++++ .../hot100/second/T35_76_MinWindow.java | 80 +++++++++++++++ .../hot100/second/T47_114_Flatten.java | 38 +++++++ .../second/T50_128_LongestConsecutive.java | 99 +++++++++++++++++++ 8 files changed, 508 insertions(+) create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T02_2_AddTwoNumbers.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T03_3_LengthOfLongestSubstring.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T26_49_GroupAnagrams.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T27_53_MaxSubArray.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T29_56_Merge.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T35_76_MinWindow.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T47_114_Flatten.java create mode 100644 Leecode/src/main/java/com/markilue/leecode/hot100/second/T50_128_LongestConsecutive.java diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T02_2_AddTwoNumbers.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T02_2_AddTwoNumbers.java new file mode 100644 index 0000000..581668e --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T02_2_AddTwoNumbers.java @@ -0,0 +1,81 @@ +package com.markilue.leecode.hot100.second; + +import com.markilue.leecode.listnode.ListNode; +import com.sun.xml.internal.bind.v2.runtime.reflect.ListTransducedAccessorImpl; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-19 10:48 + *@Description: + * TODO 力扣2 两数相加: + * 给你两个 非空 的链表,表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的,并且每个节点只能存储 一位 数字。 + * 请你将两个数相加,并以相同形式返回一个表示和的链表。 + * 你可以假设除了数字 0 之外,这两个数都不会以 0 开头。 + *@Version: 1.0 + */ +public class T02_2_AddTwoNumbers { + + public ListNode addTwoNumbers(ListNode l1, ListNode l2) { + return addWithTag(l1, l2, false); + } + + public ListNode addWithTag(ListNode l1, ListNode l2, boolean flag) { + int cur = 0; + if (flag) cur = 1; + if (l1 == null && l2 == null) { + if (flag) return new ListNode(1); + return null; + } + if (l1 == null) { + l1 = new ListNode(0); + + } + if (l2 == null) { + l2 = new ListNode(0); + } + + cur += l1.val; + cur += l2.val; + + ListNode root = new ListNode(cur % 10); + root.next = addWithTag(l1.next, l2.next, cur >= 10); + return root; + + + } + + public ListNode addTwoNumbers1(ListNode l1, ListNode l2) { + + ListNode head = null; + ListNode tail = null; + int sum; + int n1; + int n2; + boolean flag = false; + + while (l1 != null || l2 != null) { + sum = flag ? 1 : 0; + n1 = l1 == null ? 0 : l1.val; + n2 = l2 == null ? 0 : l2.val; + sum += n1 + n2; + flag = sum >= 10; + if (head == null) { + head=tail = new ListNode(sum % 10); + + } else { + tail.next = new ListNode(sum % 10); + tail = tail.next; + } + if (l1 != null) l1 = l1.next; + if (l2 != null) l2 = l2.next; + } + if(flag){ + tail.next=new ListNode(1); + } + + return head; + } + +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T03_3_LengthOfLongestSubstring.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T03_3_LengthOfLongestSubstring.java new file mode 100644 index 0000000..4bc2b96 --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T03_3_LengthOfLongestSubstring.java @@ -0,0 +1,45 @@ +package com.markilue.leecode.hot100.second; + +import org.junit.Test; + +import java.util.HashMap; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-19 11:50 + *@Description: + * TODO 力扣3 无重复字符的最长子串: + * 给定一个字符串 s ,请你找出其中不含有重复字符的 最长子串 的长度。 + *@Version: 1.0 + */ +public class T03_3_LengthOfLongestSubstring { + + @Test + public void test() { + String s = "abcabcbb"; + System.out.println(lengthOfLongestSubstring(s)); + } + + public int lengthOfLongestSubstring(String s) { + + HashMap map = new HashMap<>();// + char[] chars = s.toCharArray(); + int result = 0; + int last = 0; + for (int i = 0; i < chars.length; i++) { + if (map.containsKey(chars[i])) { + Integer lastIndex = map.get(chars[i]) + 1; + last = Math.max(lastIndex, last); + + } + int length = i - last + 1; + if (length > result) result = length; + map.put(chars[i], i); + } + + return result; + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T26_49_GroupAnagrams.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T26_49_GroupAnagrams.java new file mode 100644 index 0000000..f8205fb --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T26_49_GroupAnagrams.java @@ -0,0 +1,48 @@ +package com.markilue.leecode.hot100.second; + +import org.junit.Test; + +import java.util.*; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 10:20 + *@Description: + * TODO 力扣49题 字母异位词分组: + * 给你一个字符串数组,请你将 字母异位词 组合在一起。可以按任意顺序返回结果列表。 + * 字母异位词 是由重新排列源单词的字母得到的一个新单词,所有源单词中的字母通常恰好只用一次。 + *@Version: 1.0 + */ +public class T26_49_GroupAnagrams { + + @Test + public void test(){ + String[] strs = {"eat", "tea", "tan", "ate", "nat", "bat"}; + System.out.println(groupAnagrams(strs)); + } + + + /** + * 思路:异位词即个数相同即可,因此使用一个map记录,key就可以是strs排序后的字符 + * @param strs + * @return + */ + public List> groupAnagrams(String[] strs) { + + HashMap> map = new HashMap<>(); + + for (String str : strs) { + char[] chars = str.toCharArray(); + Arrays.sort(chars); + String key = new String(chars); + if(!map.containsKey(key)){ + map.put(key,new ArrayList<>()); + } + map.get(key).add(str); + } + return new ArrayList<>(map.values()); + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T27_53_MaxSubArray.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T27_53_MaxSubArray.java new file mode 100644 index 0000000..5b80e1e --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T27_53_MaxSubArray.java @@ -0,0 +1,61 @@ +package com.markilue.leecode.hot100.second; + +import org.junit.Test; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 10:32 + *@Description: + * TODO 力扣53 最大子数组和: + * 给你一个整数数组 nums ,请你找出一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。 + * 子数组 是数组中的一个连续部分。 + *@Version: 1.0 + */ +public class T27_53_MaxSubArray { + + @Test + public void test() { + int[] nums = {-2, 1, -3, 4, -1, 2, 1, -5, 4}; + System.out.println(maxSubArray1(nums)); + } + + + /** + * 思路:子数组贪心法 + * @param nums + * @return + */ + public int maxSubArray(int[] nums) { + + int max = nums[0]; + int cur = nums[0]; + + for (int i = 1; i < nums.length; i++) { + //这三者的前后顺序也有关系 + if (cur < 0) cur = 0; + cur += nums[i]; + if (max < cur) max = cur; + } + + return max; + } + + + public int maxSubArray1(int[] nums) { + + + int[][] dp = new int[nums.length][2]; + dp[0][0] = Integer.MIN_VALUE;//至少要一个 + dp[0][1] = nums[0]; + + for (int i = 1; i < nums.length; i++) { + dp[i][0] = Math.max(dp[i - 1][1], dp[i - 1][0]);//昨天的要今天不要,全不要 + dp[i][1] = Math.max(dp[i - 1][1] + nums[i], nums[i]);//差别在于,要不要昨天 + } + return Math.max(dp[dp.length - 1][0], dp[dp.length - 1][1]); + + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T29_56_Merge.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T29_56_Merge.java new file mode 100644 index 0000000..2af2205 --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T29_56_Merge.java @@ -0,0 +1,56 @@ +package com.markilue.leecode.hot100.second; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Comparator; +import java.util.List; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 10:49 + *@Description: + * TODO 力扣56 合并区间: + * 以数组 intervals 表示若干个区间的集合,其中单个区间为 intervals[i] = [starti, endi] 。请你合并所有重叠的区间,并返回 一个不重叠的区间数组,该数组需恰好覆盖输入中的所有区间 。 + *@Version: 1.0 + */ +public class T29_56_Merge { + + /** + * 思路:排序后按照对应的位置合并区间 + * @param intervals + * @return + */ + public int[][] merge(int[][] intervals) { + + Arrays.sort(intervals, new Comparator() { + @Override + public int compare(int[] o1, int[] o2) { + return o1[0] == o2[0] ? o1[1] - o2[1] : o1[0] - o2[0]; + } + }); + + List result = new ArrayList<>(); + result.add(intervals[0]); + int last = intervals[0][1]; + + for (int i = 1; i < intervals.length; i++) { + if (intervals[i][0] <= last) { + //需要合并 + int now = result.get(result.size() - 1)[1]; + if (now < intervals[i][1]) { + result.get(result.size() - 1)[1] = intervals[i][1]; + last = intervals[i][1]; + } + + } else { + result.add(intervals[i]); + last = intervals[i][1]; + } + } + + return result.toArray(new int[0][]); + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T35_76_MinWindow.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T35_76_MinWindow.java new file mode 100644 index 0000000..b533d7f --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T35_76_MinWindow.java @@ -0,0 +1,80 @@ +package com.markilue.leecode.hot100.second; + +import org.junit.Test; + +import java.util.HashMap; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 11:00 + *@Description: + * TODO 力扣76 最小覆盖子串: + * 给你一个字符串 s 、一个字符串 t 。返回 s 中涵盖 t 所有字符的最小子串。如果 s 中不存在涵盖 t 所有字符的子串,则返回空字符串 "" 。 + *@Version: 1.0 + */ +public class T35_76_MinWindow { + + @Test + public void test() { + String s = "aa", t = "aa"; + System.out.println(minWindow(s, t)); + } + + + /** + * 滑动窗口法 + * 维护一个需要的窗口 和一个 滑动的窗口 + * @param s + * @param t + * @return + */ + public String minWindow(String s, String t) { + HashMap need = new HashMap<>(); + + for (char c : t.toCharArray()) { + need.put(c, need.getOrDefault(c, 0) + 1); + }//记录需要的次数 + + HashMap window = new HashMap<>(); + + int left = 0; + int right = 0; + int count = 0;//记录满足要求的个数 + int start = 0; + int len = Integer.MAX_VALUE; + + while (right < s.length()) { + char c = s.charAt(right++); + if (need.containsKey(c)) { + window.put(c, window.getOrDefault(c, 0) + 1); + if (need.get(c).equals(window.get(c))) { + count++; + } + } + + //是否满足要求了 + while (count == need.size()) { + if (len > right - left + 1) { + start = left; + len = right - left + 1; + } + char c1 = s.charAt(left++); + if (need.containsKey(c1)) { + Integer num = window.get(c1); + if (num .equals(need.get(c1)) ) { + + count--; + } + window.put(c1, window.getOrDefault(c1, 0) - 1);//增加窗口中的个数 + } + } + + + } + + return len == Integer.MAX_VALUE ? "" : s.substring(start, start + len - 1); + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T47_114_Flatten.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T47_114_Flatten.java new file mode 100644 index 0000000..be1b240 --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T47_114_Flatten.java @@ -0,0 +1,38 @@ +package com.markilue.leecode.hot100.second; + +import com.markilue.leecode.tree.TreeNode; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 11:29 + *@Description: TODO 力扣114 二叉树展开为链表 + *@Version: 1.0 + */ +public class T47_114_Flatten { + + public void flatten(TreeNode root) { + + if (root == null) { + return; + } + + TreeNode temp = root; + + while (temp.right != null||temp.left!=null) { + if (temp.left != null) { + TreeNode cur = temp.left; + while (cur.right != null) { + cur = cur.right;//寻找左子树的最右节点 + } + cur.right=temp.right; + temp.right = temp.left; + temp.left=null; + } else { + temp = temp.right; + } + } + + } +} diff --git a/Leecode/src/main/java/com/markilue/leecode/hot100/second/T50_128_LongestConsecutive.java b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T50_128_LongestConsecutive.java new file mode 100644 index 0000000..72b6b3d --- /dev/null +++ b/Leecode/src/main/java/com/markilue/leecode/hot100/second/T50_128_LongestConsecutive.java @@ -0,0 +1,99 @@ +package com.markilue.leecode.hot100.second; + +import java.math.BigDecimal; +import java.math.RoundingMode; +import java.util.HashMap; +import java.util.HashSet; + +/** + *@BelongsProject: Leecode + *@BelongsPackage: com.markilue.leecode.hot100.second + *@Author: markilue + *@CreateTime: 2023-04-18 11:41 + *@Description: + * TODO 力扣128 最长连续序列: + * 给定一个未排序的整数数组 nums ,找出数字连续的最长序列(不要求序列元素在原数组中连续)的长度。 + * 请你设计并实现时间复杂度为 O(n) 的算法解决此问题。 + *@Version: 1.0 + */ +public class T50_128_LongestConsecutive { + + + /** + * 思路:用hashset记录所有,记录最大的值 + * @param nums + * @return + */ + public int longestConsecutive(int[] nums) { + + HashMap map = new HashMap<>(); + int min = Integer.MAX_VALUE; + + for (int i = 0; i < nums.length; i++) { + map.put(nums[i], i); + if (min > nums[i]) min = nums[i]; + } + + int result = 0; + + //从最小值开始遍历寻找合适的 + boolean[] used = new boolean[nums.length + 1]; + + for (int i = 0; i < nums.length; i++) { + if (!used[i]) { + //寻找比他小的值和比他大的值 + int cur = 1; + int tempLow = nums[i]; + while (map.containsKey(tempLow - 1)) { + cur++; + used[map.get(tempLow - 1)] = true; + tempLow--; + } + + int tempHight = nums[i]; + while (map.containsKey(tempHight + 1)) { + cur++; + used[map.get(tempLow + 1)] = true; + tempHight++; + } + if (cur > result) result = cur; + } + } + + return result; + + + } + + public int longestConsecutive1(int[] nums) { + + HashSet set = new HashSet<>(); + + for (int num : nums) { + set.add(num); + } + + int result = 0; + + //从最小值开始遍历寻找合适的 + for (Integer s : set) { + + if(!set.contains(s-1)){//只从最小的开始找 + int cur = 1; + int tempHight = s; + while (set.contains(tempHight + 1)) { + cur++; + tempHight++; + } + set.remove(s); + if (cur > result) result = cur; + } + + } + + + return result; + + + } +}