From 4d0768b8f7acc4df03b48d0502b07e1020380407 Mon Sep 17 00:00:00 2001 From: algorithmzuo Date: Wed, 14 Sep 2022 22:54:05 +0800 Subject: [PATCH] modify code --- .../class_2022_09_2_week/Code01_SortGame.java | 189 ++++++++++++++ .../Code02_NLengthMValueLIS3.java | 148 +++++++++++ .../Code03_EvenTimesMaxSubstring.java | 94 +++++++ .../Code04_RunThroughZero1.java | 127 ++++++++++ .../Code04_RunThroughZero2.java | 234 ++++++++++++++++++ ...养的大厂算法面试题(正在直播) | 39 +++ 6 files changed, 831 insertions(+) create mode 100644 算法周更班/class_2022_09_2_week/Code01_SortGame.java create mode 100644 算法周更班/class_2022_09_2_week/Code02_NLengthMValueLIS3.java create mode 100644 算法周更班/class_2022_09_2_week/Code03_EvenTimesMaxSubstring.java create mode 100644 算法周更班/class_2022_09_2_week/Code04_RunThroughZero1.java create mode 100644 算法周更班/class_2022_09_2_week/Code04_RunThroughZero2.java diff --git a/算法周更班/class_2022_09_2_week/Code01_SortGame.java b/算法周更班/class_2022_09_2_week/Code01_SortGame.java new file mode 100644 index 0000000..a8b82eb --- /dev/null +++ b/算法周更班/class_2022_09_2_week/Code01_SortGame.java @@ -0,0 +1,189 @@ +package class_2022_09_2_week; + +import java.util.Arrays; +import java.util.Comparator; +import java.util.TreeSet; + +// 来自百度 +// 二狗买了一些小兵玩具,和大胖一起玩 +// 一共有n个小兵,这n个小兵拍成一列 +// 第i个小兵战斗力为hi,然后他们两个开始对小兵进行排列 +// 一共进行m次操作,二狗每次操作选择一个数k,将前k个小兵战斗力从小到大排列 +// 大胖每次操作选择一个数k,将前k个小兵战斗力从大到小排列 +// 问所有操作结束后,排列顺序什么样 +// 给定一个长度为n的数组arr,表示每个小兵的战斗力 +// 给定一个长度为m的数组op, +// op[i] = { k , 0 }, 表示对前k个士兵执行从小到大的操作 +// op[i] = { k , 1 }, 表示对前k个士兵执行从大到小的操作 +// 返回数组ans,表示最终的排列 +// 1 <= n, m <= 2 * 10^5 +// - 10^9 <= arr[i] <= + 10^9 +public class Code01_SortGame { + + // 暴力方法 + // 为了验证 + public static int[] game1(int[] arr, int[][] op) { + int n = arr.length; + Integer[] help = new Integer[n]; + for (int i = 0; i < n; i++) { + help[i] = arr[i]; + } + for (int[] o : op) { + if (o[1] == 0) { + Arrays.sort(help, 0, o[0], (a, b) -> a - b); + } else { + Arrays.sort(help, 0, o[0], (a, b) -> b - a); + } + } + int[] ans = new int[n]; + for (int i = 0; i < n; i++) { + ans[i] = help[i]; + } + return ans; + } + + // 正式方法 + // 时间复杂度O(M) + O(N*logN) + public static int[] game2(int[] arr, int[][] op) { + int n = arr.length; + int m = op.length; + int[] stack = new int[m]; + int r = 0; + for (int i = 0; i < m; i++) { + while (r != 0 && op[stack[r - 1]][0] <= op[i][0]) { + r--; + } + stack[r++] = i; + } + int[] ans = new int[n]; + int ansi = n - 1; + int l = 0; + for (; ansi >= op[stack[l]][0]; ansi--) { + ans[ansi] = arr[ansi]; + } + TreeSet sorted = new TreeSet<>(new NumberComparator()); + for (int i = 0; i < op[stack[l]][0]; i++) { + sorted.add(new Number(arr[i], i)); + } + while (l != r) { + // 当前处理的指令 + int[] cur = op[stack[l++]]; + if (l != r) { + int[] next = op[stack[l]]; + int num = cur[0] - next[0]; + if (cur[1] == 0) { + for (int i = 0; i < num; i++) { + ans[ansi--] = sorted.pollLast().value; + } + } else { + for (int i = 0; i < num; i++) { + ans[ansi--] = sorted.pollFirst().value; + } + } + } else { + if (cur[1] == 0) { + while (!sorted.isEmpty()) { + ans[ansi--] = sorted.pollLast().value; + } + } else { + while (!sorted.isEmpty()) { + ans[ansi--] = sorted.pollFirst().value; + } + } + } + } + return ans; + } + + public static class Number { + public int value; + public int index; + + public Number(int v, int i) { + value = v; + index = i; + } + } + + public static class NumberComparator implements Comparator { + + @Override + public int compare(Number o1, Number o2) { + if (o1.value != o2.value) { + return o1.value - o2.value; + } else { + return o1.index - o2.index; + } + } + + } + + // 为了测试 + public static int[] randomArray(int n, int v) { + int[] ans = new int[n]; + for (int i = 0; i < n; i++) { + ans[i] = (int) (Math.random() * v) + 1; + } + return ans; + } + + // 为了测试 + public static int[][] randomOp(int m, int n) { + int[][] ans = new int[m][2]; + for (int i = 0; i < m; i++) { + ans[i][0] = (int) (Math.random() * (n + 1)); + ans[i][1] = Math.random() < 0.5 ? 0 : 1; + } + return ans; + } + + // 为了测试 + public static boolean isEqual(int[] arr1, int[] arr2) { + if (arr1.length != arr2.length) { + return false; + } + for (int i = 0; i < arr1.length; i++) { + if (arr1[i] != arr2[i]) { + return false; + } + } + return true; + } + + // 为了测试 + public static void main(String[] args) { + +// int[] arr = { 3, 3, 7, 7, 7 }; +// +// TreeSet set = new TreeSet<>(new NumberComparator()); +// +// for (int i = 0; i < arr.length; i++) { +// set.add(new Number(arr[i], i)); +// } +// +//// System.out.println(set.size()); +// +// while(!set.isEmpty()) { +// System.out.println(set.pollLast().value); +// } + + int N = 100; + int M = 100; + int V = 200; + int testTimes = 5000; + System.out.println("测试开始"); + for (int i = 0; i < testTimes; i++) { + int n = (int) (Math.random() * N) + 1; + int m = (int) (Math.random() * M) + 1; + int[] arr = randomArray(n, V); + int[][] op = randomOp(m, n); + int[] ans1 = game1(arr, op); + int[] ans2 = game2(arr, op); + if (!isEqual(ans1, ans2)) { + System.out.println("出错了!"); + } + } + System.out.println("测试结束"); + } + +} diff --git a/算法周更班/class_2022_09_2_week/Code02_NLengthMValueLIS3.java b/算法周更班/class_2022_09_2_week/Code02_NLengthMValueLIS3.java new file mode 100644 index 0000000..3aed36f --- /dev/null +++ b/算法周更班/class_2022_09_2_week/Code02_NLengthMValueLIS3.java @@ -0,0 +1,148 @@ +package class_2022_09_2_week; + +// 来自微众银行 +// 给定一个数字n,代表数组的长度 +// 给定一个数字m,代表数组每个位置都可以在1~m之间选择数字 +// 所有长度为n的数组中,最长递增子序列长度为3的数组,叫做达标数组 +// 返回达标数组的数量 +// 1 <= n <= 500 +// 1 <= m <= 10 +// 500 * 10 * 10 * 10 +// 结果对998244353取模 +// 实现的时候没有取模的逻辑,因为非重点 +public class Code02_NLengthMValueLIS3 { + + // 暴力方法 + // 为了验证 + public static int number1(int n, int m) { + return process1(0, n, m, new int[n]); + } + + public static int process1(int i, int n, int m, int[] path) { + if (i == n) { + return lengthOfLIS(path) == 3 ? 1 : 0; + } else { + int ans = 0; + for (int cur = 1; cur <= m; cur++) { + path[i] = cur; + ans += process1(i + 1, n, m, path); + } + return ans; + } + } + + public static int lengthOfLIS(int[] arr) { + if (arr == null || arr.length == 0) { + return 0; + } + int[] ends = new int[arr.length]; + ends[0] = arr[0]; + int right = 0; + int max = 1; + for (int i = 1; i < arr.length; i++) { + int l = 0; + int r = right; + while (l <= r) { + int m = (l + r) / 2; + if (arr[i] > ends[m]) { + l = m + 1; + } else { + r = m - 1; + } + } + right = Math.max(right, l); + ends[l] = arr[i]; + max = Math.max(max, l + 1); + } + return max; + } + + // i : 当前来到的下标 + // f、s、t : ends数组中放置的数字! + // ? == 0,没放! + // n : 一共的长度! + // m : 每一位,都可以在1~m中随意选择数字 + // 返回值:i..... 有几个合法的数组! + public static int zuo(int i, int f, int s, int t, int n, int m) { + if (i == n) { + return f != 0 && s != 0 && t != 0 ? 1 : 0; + } + // i < n + int ans = 0; + for (int cur = 1; cur <= m; cur++) { + if (f == 0 || f >= cur) { + ans += zuo(i + 1, cur, s, t, n, m); + } else if (s == 0 || s >= cur) { + ans += zuo(i + 1, f, cur, t, n, m); + } else if (t == 0 || t >= cur) { + ans += zuo(i + 1, f, s, cur, n, m); + } + } + return ans; + } + + // 正式方法 + // 需要看最长递增子序列! + // 尤其是理解ends数组的意义! + public static int number2(int n, int m) { + int[][][][] dp = new int[n][m + 1][m + 1][m + 1]; + for (int i = 0; i < n; i++) { + for (int f = 0; f <= m; f++) { + for (int s = 0; s <= m; s++) { + for (int t = 0; t <= m; t++) { + dp[i][f][s][t] = -1; + } + } + } + } + return process2(0, 0, 0, 0, n, m, dp); + } + + public static int process2(int i, int f, int s, int t, int n, int m, int[][][][] dp) { + if (i == n) { + return f != 0 && s != 0 && t != 0 ? 1 : 0; + } + if (dp[i][f][s][t] != -1) { + return dp[i][f][s][t]; + } + int ans = 0; + for (int cur = 1; cur <= m; cur++) { + if (f == 0 || cur <= f) { + ans += process2(i + 1, cur, s, t, n, m, dp); + } else if (s == 0 || cur <= s) { + ans += process2(i + 1, f, cur, t, n, m, dp); + } else if (t == 0 || cur <= t) { + ans += process2(i + 1, f, s, cur, n, m, dp); + } + } + dp[i][f][s][t] = ans; + return ans; + } + + public static void main(String[] args) { + System.out.println("功能测试开始"); + for (int n = 4; n <= 8; n++) { + for (int m = 1; m <= 5; m++) { + int ans1 = number1(n, m); + int ans2 = number2(n, m); + if (ans1 != ans2) { + System.out.println(ans1); + System.out.println(ans2); + System.out.println("出错了!"); + } + } + } + System.out.println("功能测试结束"); + System.out.println("性能测试开始"); + int n = 2000; + int m = 20; + System.out.println("序列长度 : " + n); + System.out.println("数字范围 : " + m); + long start = System.currentTimeMillis(); + number2(n, m); + long end = System.currentTimeMillis(); + System.out.println("运行时间 : " + (end - start) + " 毫秒"); + System.out.println("性能测试结束"); + } + +} diff --git a/算法周更班/class_2022_09_2_week/Code03_EvenTimesMaxSubstring.java b/算法周更班/class_2022_09_2_week/Code03_EvenTimesMaxSubstring.java new file mode 100644 index 0000000..c42f55e --- /dev/null +++ b/算法周更班/class_2022_09_2_week/Code03_EvenTimesMaxSubstring.java @@ -0,0 +1,94 @@ +package class_2022_09_2_week; + +import java.util.HashMap; + +// 来自微软 +// 给定一个字符串s,其中都是英文小写字母 +// 如果s中的子串含有的每种字符都是偶数个 +// 那么这样的子串就是达标子串,子串要求是连续串 +// 返回s中达标子串的最大长度 +// 1 <= s的长度 <= 10^5 +// 字符种类都是英文小写 +public class Code03_EvenTimesMaxSubstring { + + // 为了测试 + // 暴力方法 + public static int maxLen1(String s) { + int n = s.length(); + int ans = 0; + for (int i = 0; i < n; i++) { + for (int j = n - 1; j >= i; j--) { + if (ok(s, i, j)) { + ans = Math.max(ans, j - i + 1); + break; + } + } + } + return ans; + } + + // 为了测试 + // 暴力方法 + public static boolean ok(String s, int l, int r) { + if (((r - l + 1) & 1) == 1) { + return false; + } + int[] cnts = new int[26]; + for (int i = l; i <= r; i++) { + cnts[s.charAt(i) - 'a']++; + } + for (int cnt : cnts) { + if ((cnt & 1) == 1) { + return false; + } + } + return true; + } + + public static int maxLen2(String s) { + HashMap map = new HashMap<>(); + map.put(0, -1); + int status = 0; + int ans = 0; + int n = s.length(); + for (int i = 0; i < n; i++) { + status ^= 1 << (s.charAt(i) - 'a'); + if (map.containsKey(status)) { + ans = Math.max(ans, i - map.get(status)); + } else { + map.put(status, i); + } + } + return ans; + } + + // 为了测试 + public static String randomString(int n, int v) { + char[] s = new char[n]; + for (int i = 0; i < n; i++) { + s[i] = (char) ((int) (Math.random() * v) + 'a'); + } + return String.valueOf(s); + } + + // 为了测试 + public static void main(String[] args) { + int n = 50; + int v = 6; + int testTimes = 2000; + System.out.println("测试开始"); + for (int i = 0; i < testTimes; i++) { + String s = randomString(n, v); + int ans1 = maxLen1(s); + int ans2 = maxLen2(s); + if (ans1 != ans2) { + System.out.println(s); + System.out.println(ans1); + System.out.println(ans2); + break; + } + } + System.out.println("测试结束"); + } + +} diff --git a/算法周更班/class_2022_09_2_week/Code04_RunThroughZero1.java b/算法周更班/class_2022_09_2_week/Code04_RunThroughZero1.java new file mode 100644 index 0000000..55b4c59 --- /dev/null +++ b/算法周更班/class_2022_09_2_week/Code04_RunThroughZero1.java @@ -0,0 +1,127 @@ +package class_2022_09_2_week; + +// 来自学员问题 +// 本文件仅为贪心的验证文件 +// 有一个数组包含0、1、2三种值, +// 有n次修改机会,第一种将所有连通的1变为0,修改次数-1 +// 第二种将所有连通的2变为1或0,修改次数-2, +// 返回n次修改机会的情况下连通的0最长能是多少? +// 1 <= arr长度 <=10^6 +// 0 <= 修改机会 <=10^6 +public class Code04_RunThroughZero1 { + + public static int best1(int[] arr) { + int zero = 0; + int two = 0; + int n = arr.length; + for (int num : arr) { + zero += num == 0 ? 1 : 0; + two += num == 2 ? 1 : 0; + } + if (zero == n) { + return 0; + } + if (two == n) { + return 2; + } + int ans = Integer.MAX_VALUE; + for (int i = 0; i < n; i++) { + if (arr[i] != 0 && (i == 0 || arr[i - 1] != arr[i])) { + if (arr[i] == 2) { + ans = Math.min(ans, 2 + Math.min(best1(change(arr, i, 1)), best1(change(arr, i, 0)))); + } else { + ans = Math.min(ans, 1 + best1(change(arr, i, 0))); + } + } + } + return ans; + } + + public static int[] change(int[] arr, int i, int to) { + int l = i; + int r = i; + while (l >= 0 && arr[l] == arr[i]) { + l--; + } + while (r < arr.length && arr[r] == arr[i]) { + r++; + } + int[] ans = new int[arr.length]; + for (i = 0; i < arr.length; i++) { + ans[i] = arr[i]; + } + for (i = l + 1; i < r; i++) { + ans[i] = to; + } + return ans; + } + + public static int cost(int[] arr, int l, int r) { + int num0 = 0; + int num2 = 0; + int n = r - l + 1; + for (int i = l; i <= r; i++) { + num0 += arr[i] == 0 ? 1 : 0; + num2 += arr[i] == 2 ? 1 : 0; + } + if (num0 == n) { + return 0; + } + if (num2 == n) { + return 2; + } + int area2 = arr[l] == 2 ? 1 : 0; + for (int i = l; i < r; i++) { + if (arr[i] != 2 && arr[i + 1] == 2) { + area2++; + } + } + boolean has1 = false; + int areaHas1No0 = 0; + for (int i = l; i <= r; i++) { + if (arr[i] == 0) { + if (has1) { + areaHas1No0++; + } + has1 = false; + } + if (arr[i] == 1) { + has1 = true; + } + } + if (has1) { + areaHas1No0++; + } + return 2 * area2 + areaHas1No0; + } + + public static int[] randomArray(int n) { + int[] ans = new int[n]; + for (int i = 0; i < n; i++) { + ans[i] = (int) (Math.random() * 3); + } + return ans; + } + + public static void main(String[] args) { + int n = 9; + int testTimes = 1000; + System.out.println("测试开始"); + for (int i = 0; i < testTimes; i++) { + int[] arr = randomArray(n); + int ans1 = best1(arr); + int ans2 = cost(arr, 0, arr.length - 1); + if (ans1 != ans2) { + for (int num : arr) { + System.out.print(num + " "); + } + System.out.println(); + System.out.println(ans1); + System.out.println(ans2); + break; + } + } + System.out.println("测试结束"); + } + +} diff --git a/算法周更班/class_2022_09_2_week/Code04_RunThroughZero2.java b/算法周更班/class_2022_09_2_week/Code04_RunThroughZero2.java new file mode 100644 index 0000000..e89c4a0 --- /dev/null +++ b/算法周更班/class_2022_09_2_week/Code04_RunThroughZero2.java @@ -0,0 +1,234 @@ +package class_2022_09_2_week; + +// 来自学员问题 +// 有一个数组包含0、1、2三种值, +// 有m次修改机会,第一种将所有连通的1变为0,修改次数-1 +// 第二种将所有连通的2变为1或0,修改次数-2, +// 返回m次修改机会的情况下,让最大的0连通区,最长能是多少? +// 1 <= arr长度 <= 10^6 +// 0 <= 修改机会 <= 10^6 +public class Code04_RunThroughZero2 { + + // 时间复杂度O(N^3)的方法 + // 为了验证 + public static int maxZero1(int[] arr, int k) { + int n = arr.length; + int ans = 0; + for (int i = 0; i < n; i++) { + for (int j = n - 1; j >= i; j--) { + if (cost1(arr, i, j) <= k) { + ans = Math.max(ans, j - i + 1); + break; + } + } + } + return ans; + } + + // 为了验证 + public static int cost1(int[] arr, int l, int r) { + int num0 = 0; + int num2 = 0; + int n = r - l + 1; + for (int i = l; i <= r; i++) { + num0 += arr[i] == 0 ? 1 : 0; + num2 += arr[i] == 2 ? 1 : 0; + } + if (num0 == n) { + return 0; + } + if (num2 == n) { + return 2; + } + int area2 = arr[l] == 2 ? 1 : 0; + for (int i = l; i < r; i++) { + if (arr[i] != 2 && arr[i + 1] == 2) { + area2++; + } + } + boolean has1 = false; + int areaHas1No0 = 0; + for (int i = l; i <= r; i++) { + if (arr[i] == 0) { + if (has1) { + areaHas1No0++; + } + has1 = false; + } + if (arr[i] == 1) { + has1 = true; + } + } + if (has1) { + areaHas1No0++; + } + return 2 * area2 + areaHas1No0; + } + + // 正式方法 + // 时间复杂度O(N) + public static int[] left10 = new int[1000001]; + public static int[] left2x = new int[1000001]; + public static int[] right10 = new int[1000001]; + public static int[] right2x = new int[1000001]; + public static int[] area2s = new int[1000001]; + public static int[] area1s = new int[1000001]; + + public static int maxZero2(int[] arr, int k) { + int n = arr.length; + int last = -1; + for (int i = 0; i < n; i++) { + if (arr[i] == 0) { + last = i; + } + if (arr[i] == 1) { + left10[i] = last; + } + } + last = -1; + for (int i = 0; i < n; i++) { + if (arr[i] != 2) { + last = i; + } + if (arr[i] == 2) { + left2x[i] = last; + } + } + last = n; + for (int i = n - 1; i >= 0; i--) { + if (arr[i] == 0) { + last = i; + } + if (arr[i] == 1) { + right10[i] = last; + } + } + last = n; + for (int i = n - 1; i >= 0; i--) { + if (arr[i] != 2) { + last = i; + } + if (arr[i] == 2) { + right2x[i] = last; + } + } + int area2 = arr[0] == 2 ? 1 : 0; + for (int i = 0; i < n - 1; i++) { + if (arr[i] != 2) { + area2s[i] = area2; + if (arr[i + 1] == 2) { + area2++; + } + } + } + if (arr[n - 1] != 2) { + area2s[n - 1] = area2; + } + boolean has1 = false; + int area1 = 0; + for (int i = 0; i < n; i++) { + if (arr[i] == 0) { + if (has1) { + area1++; + } + has1 = false; + area1s[i] = area1; + } + if (arr[i] == 1) { + has1 = true; + } + } + int ans = 0; + int right = 0; + for (int left = 0; left < n; left++) { + while (right < n && cost2(arr, left, right) <= k) { + right++; + } + ans = Math.max(ans, right - left); + right = Math.max(right, left + 1); + } + return ans; + } + + public static int cost2(int[] arr, int left, int right) { + if (arr[left] == 2 && right2x[left] > right) { + return 2; + } + int area2 = arr[left] == 2 ? 1 : 0; + area2 += arr[right] == 2 ? 1 : 0; + left = arr[left] == 2 ? right2x[left] : left; + right = arr[right] == 2 ? left2x[right] : right; + area2 += area2s[right] - area2s[left]; + int area1 = 0; + if (arr[left] == 0 && arr[right] == 0) { + area1 = area1s[right] - area1s[left]; + } else if (arr[left] == 0) { + area1++; + right = left10[right]; + area1 += area1s[right] - area1s[left]; + } else if (arr[right] == 0) { + area1++; + left = right10[left]; + area1 += area1s[right] - area1s[left]; + } else { + if (right10[left] > right) { + area1++; + } else { + area1 += 2; + left = right10[left]; + right = left10[right]; + area1 += area1s[right] - area1s[left]; + } + } + return 2 * area2 + area1; + } + + // 为了测试 + public static int[] randomArray(int n) { + int[] ans = new int[n]; + for (int i = 0; i < n; i++) { + ans[i] = (int) (Math.random() * 3); + } + return ans; + } + + // 为了测试 + public static void main(String[] args) { + int N = 100; + int K = 100; + int testTimes = 5000; + System.out.println("功能测试开始"); + for (int i = 0; i < testTimes; i++) { + int n = (int) (Math.random() * N) + 1; + int k = (int) (Math.random() * K); + int[] arr = randomArray(n); + int ans1 = maxZero1(arr, k); + int ans2 = maxZero2(arr, k); + if (ans1 != ans2) { + for (int num : arr) { + System.out.print(num + " "); + } + System.out.println(); + System.out.println("k : " + k); + System.out.println(ans1); + System.out.println(ans2); + break; + } + } + System.out.println("功能测试结束"); + + System.out.println("性能测试开始"); + int n = 1000000; + int k = 1000000; + System.out.println("数组长度 : " + n); + System.out.println("修改次数 : " + k); + int[] arr = randomArray(n); + long start = System.currentTimeMillis(); + maxZero2(arr, k); + long end = System.currentTimeMillis(); + System.out.println("运行时间 : " + (end - start) + "毫秒"); + System.out.println("性能测试结束"); + + } + +} diff --git a/算法课堂笔记/课堂内容汇总/每周有营养的大厂算法面试题(正在直播) b/算法课堂笔记/课堂内容汇总/每周有营养的大厂算法面试题(正在直播) index c35fdac..dcab08c 100644 --- a/算法课堂笔记/课堂内容汇总/每周有营养的大厂算法面试题(正在直播) +++ b/算法课堂笔记/课堂内容汇总/每周有营养的大厂算法面试题(正在直播) @@ -1853,6 +1853,45 @@ graph[i] = {a,b,c,d} 表示i讨厌(a,b,c,d),讨厌关系为双向的 +第040节 2022年9月第2周流行算法题目解析 +来自百度 +二狗买了一些小兵玩具,和大胖一起玩 +一共有n个小兵,这n个小兵拍成一列 +第i个小兵战斗力为hi,然后他们两个开始对小兵进行排列 +一共进行m次操作,二狗每次操作选择一个数k,将前k个小兵战斗力从小到大排列 +大胖每次操作选择一个数k,将前k个小兵战斗力从大到小排列 +问所有操作结束后,排列顺序什么样 +给定一个长度为n的数组arr,表示每个小兵的战斗力 +给定一个长度为m的数组op, +op[i] = { k , 0 }, 表示对前k个士兵执行从小到大的操作 +op[i] = { k , 1 }, 表示对前k个士兵执行从大到小的操作 +返回数组ans,表示最终的排列 +1 <= n, m <= 2 * 10^5 +- 10^9 <= arr[i] <= + 10^9 + +来自微众银行 +给定一个数字n,代表数组的长度 +给定一个数字m,代表数组每个位置都可以在1~m之间选择数字 +所有长度为n的数组中,最长递增子序列长度为3的数组,叫做达标数组 +返回达标数组的数量 +1 <= n <= 500 +1 <= m <= 10 + +来自微软 +给定一个字符串s,其中都是英文小写字母 +如果s中的子串含有的每种字符都是偶数个 +那么这样的子串就是达标子串,子串要求是连续串 +返回s中达标子串的最大长度 +1 <= s的长度 <= 10^5 +字符种类都是英文小写 + +来自学员问题 +有一个数组包含0、1、2三种值, +有m次修改机会,第一种将所有连通的1变为0,修改次数-1 +第二种将所有连通的2变为1或0,修改次数-2, +返回m次修改机会的情况下,让最大的0连通区,最长能是多少? +1 <= arr长度 <= 10^6 +0 <= 修改机会 <= 10^6