classSolution{ publicint[] searchRange(int[] nums, int target) { int[] ans = newint[]{-1, -1}; int n = nums.length; if (n == 0) return ans;
int l = 0, r = n - 1; while (l < r) { int mid =( l + r ) / 2; if (nums[mid] >= target) { r = mid; } else { l = mid + 1; } } if (nums[l] != target) { return ans; } else { ans[0] = l; l = 0; r = n - 1; while (l < r) { int mid =( l + r + 1 ) / 2; if (nums[mid] <= target) { l = mid; } else { r = mid - 1; } } ans[1] = l; return ans; } } }
classSolution{ publicintremoveElement(int[] nums, int val){ int index=0; for(int i=0;i<nums.length;i++){ if(nums[i]!=val){ nums[index++]=nums[i]; } } return index; } }
总结
双指针法(快慢指针法):通过一个快指针和慢指针在一个for循环下完成两个for循环的工作。 与26. 删除排序数组中的重复项类似,如果当前元素 x 与移除元素 val 相同,那么跳过该元素。如果当前元素 x 与移除元素 val 不同,那么我们将其放到下标 index 的位置,并让 index 自增右移。最终得到的 index 即是答案。 暴力:两层for循环,第二层for循环时,遇到相同数值,则将此元素之后的数前移一位。
classSolution{ publicinttotalFruit(int[] tree){ if (tree == null || tree.length == 0) return0; int n = tree.length;
Map<Integer, Integer> map = new HashMap<>(); int maxLen = 0, left = 0; for (int i = 0; i < n; i++) { map.put(tree[i], map.getOrDefault(tree[i], 0) + 1); // 右边界 while (map.size() > 2) { // 不符合条件:水果种类大于2 map.put(tree[left], map.get(tree[left]) - 1); if (map.get(tree[left]) == 0) map.remove(tree[left]); left++; // 左边界 } maxLen = Math.max(maxLen, i - left + 1); // 更新结果 } return maxLen; } }
总结
用HashMap,Map<水果种类,出现频次>,延伸右边界时,增加频次。缩进左边界时,减少频次。频次为0时,从map删除。 getOrDefault(Object key, V defaultValue),当Map集合中有这个key时,就使用这个key对应的value值,如果没有就使用默认值defaultValue。
classSolution{ public List<Integer> spiralOrder(int[][] matrix){ List<Integer> list = new ArrayList<Integer>(); if(matrix == null || matrix.length == 0) return list; int m = matrix.length;//行数 int n = matrix[0].length;//列数 int i = 0;
将矩阵从外部向内部逐层遍历打印矩阵,最外面一圈打印完,里面仍然是一个矩阵。 m - 1 - i 是指随着层数增加时,层数的边界所在行(即最上行和最下行的所处的行数),如果出现最上行和最下行是同一行的情况(比如:3行5列的矩阵中,第二层是1行3列的矩阵),此时按顺序打印完第二层第一行后,第一列为空,不打印,折返后如果没有(m - 1 - i != i)这个限制,会重新打印第二层的第一行,造成结果的值变多。同理可得,n - 1 - i != i。
classSolution{ publicintdivide(int dividend, int divisor){ long x = dividend, y = divisor; boolean isNeg = false; if ((x > 0 && y < 0) || (x < 0 && y > 0)) isNeg = true; if (x < 0) x = -x; if (y < 0) y = -y; long l = 0, r = x; while (l < r) { long mid = l + r + 1 >> 1; if (mul(mid, y) <= x) { l = mid; } else { r = mid - 1; } } long idx = isNeg ? -l : l; if (idx > Integer.MAX_VALUE || idx < Integer.MIN_VALUE) return Integer.MAX_VALUE; return (int)idx; } longmul(long a, long k){ long ans = 0; while (k > 0) { if ((k & 1) == 1) ans += a; k >>= 1; a += a; } return ans; } }