给你一个整数数组 nums ,请你找出一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。
示例:
public static int maxSubArray(int[] nums) {
if (nums == null || nums.length == 0) {
throw new IllegalArgumentException("Array is empty");
}
int n = nums.length;
int[] dp = new int[n];
dp[0] = nums[0];
int maxSum = dp[0];
for (int i = 1; i < n; i++) {
dp[i] = Math.max(nums[i], dp[i - 1] + nums[i]);
maxSum = Math.max(maxSum, dp[i]);
}
return maxSum;
}
以数组 intervals 表示若干个区间的集合,其中单个区间为 intervals[i] = [starti, endi] 。请你合并所有重叠的区间,并返回 一个不重叠的区间数组,该数组需恰好覆盖输入中的所有区间 。
示例:
public static int[][] merge(int[][] intervals) {
if (intervals == null || intervals.length == 0) {
return new int[0][0];
}
// Sort intervals by starting time
Arrays.sort(intervals, Comparator.comparingInt(a -> a[0]));
List<int[]> merged = new LinkedList<>();
int[] currentInterval = intervals[0];
merged.add(currentInterval);
for (int i = 1; i < intervals.length; i++) {
int[] interval = intervals[i];
// If the current interval overlaps with the new interval
if (currentInterval[1] >= interval[0]) {
// Merge the current interval with the new interval
currentInterval[1] = Math.max(currentInterval[1], interval[1]);
} else {
// If no overlap, add the current interval to the result
// and start a new interval
currentInterval = interval;
merged.add(currentInterval);
}
}
return merged.toArray(new int[merged.size()][]);
}
给定一个整数数组 nums,将数组中的元素向右轮转 k 个位置,其中 k 是非负数。
示例:
向右轮转 1 步: [7,1,2,3,4,5,6]
向右轮转 2 步: [6,7,1,2,3,4,5]
向右轮转 3 步: [5,6,7,1,2,3,4]
public class ArrayRotation {
// 向右轮转数组
public static void rotate(int[] nums, int k) {
int n = nums.length;
if (n == 0 || k % n == 0) {
return; // 如果数组为空或 k 是数组长度的倍数,则不需要旋转
}
k = k % n; // 处理 k 大于数组长度的情况
reverse(nums, 0, n - 1); // 反转整个数组
reverse(nums, 0, k - 1); // 反转前 k 个元素
reverse(nums, k, n - 1); // 反转后 n - k 个元素
}
// 反转数组的部分
private static void reverse(int[] nums, int start, int end) {
while (start < end) {
int temp = nums[start];
nums[start] = nums[end];
nums[end] = temp;
start++;
end--;
}
}
}
给你一个整数数组 nums,返回 数组 answer ,其中 answer[i] 等于 nums 中除 nums[i] 之外其余各元素的乘积 。
题目数据 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在 32 位 整数范围内。
请 不要使用除法,且在 O(n) 时间复杂度内完成此题。
示例:
public class ProductArray {
// 计算除自身以外的数组乘积
public static int[] productExceptSelf(int[] nums) {
int n = nums.length;
int[] leftProducts = new int[n];
int[] rightProducts = new int[n];
int[] result = new int[n];
// 计算左侧乘积
leftProducts[0] = 1;
for (int i = 1; i < n; i++) {
leftProducts[i] = leftProducts[i - 1] * nums[i - 1];
}
// 计算右侧乘积
rightProducts[n - 1] = 1;
for (int i = n - 2; i >= 0; i--) {
rightProducts[i] = rightProducts[i + 1] * nums[i + 1];
}
// 计算结果数组
for (int i = 0; i < n; i++) {
result[i] = leftProducts[i] * rightProducts[i];
}
return result;
}
}
给你一个未排序的整数数组 nums ,请你找出其中没有出现的最小的正整数。
示例:
public static int firstMissingPositive(int[] nums) {
int n = nums.length;
// 标记所有小于等于 0 或大于 n 的数为 n + 1
for (int i = 0; i < n; i++) {
if (nums[i] <= 0 || nums[i] > n) {
nums[i] = n + 1;
}
}
// 将每个正整数映射到对应的索引位置
for (int i = 0; i < n; i++) {
int num = Math.abs(nums[i]);
if (num <= n) {
nums[num - 1] = -Math.abs(nums[num - 1]);
}
}
// 查找第一个未出现的正整数
for (int i = 0; i < n; i++) {
if (nums[i] > 0) {
return i + 1;
}
}
// 如果所有 1 到 n 的正整数都出现了,则返回 n + 1
return n + 1;
}
给定一个 m x n 的矩阵,如果一个元素为 0 ,则将其所在行和列的所有元素都设为 0 。请使用 原地 算法。
public class MatrixZeroes {
public static void setZeroes(int[][] matrix) {
if (matrix == null || matrix.length == 0) {
return;
}
int m = matrix.length;
int n = matrix[0].length;
boolean firstRowZero = false;
boolean firstColZero = false;
// Check if the first row needs to be zeroed
for (int j = 0; j < n; j++) {
if (matrix[0][j] == 0) {
firstRowZero = true;
break;
}
}
// Check if the first column needs to be zeroed
for (int i = 0; i < m; i++) {
if (matrix[i][0] == 0) {
firstColZero = true;
break;
}
}
// Use the first row and first column as markers
for (int i = 1; i < m; i++) {
for (int j = 1; j < n; j++) {
if (matrix[i][j] == 0) {
matrix[i][0] = 0; // Mark the row
matrix[0][j] = 0; // Mark the column
}
}
}
// Zero out cells based on markers in the first row and first column
for (int i = 1; i < m; i++) {
for (int j = 1; j < n; j++) {
if (matrix[i][0] == 0 || matrix[0][j] == 0) {
matrix[i][j] = 0;
}
}
}
// Zero out the first row if needed
if (firstRowZero) {
for (int j = 0; j < n; j++) {
matrix[0][j] = 0;
}
}
// Zero out the first column if needed
if (firstColZero) {
for (int i = 0; i < m; i++) {
matrix[i][0] = 0;
}
}
}
}
给定一个 n × n 的二维矩阵 matrix 表示一个图像。请你将图像顺时针旋转 90 度。
你必须在 原地 旋转图像,这意味着你需要直接修改输入的二维矩阵。请不要 使用另一个矩阵来旋转图像。
示例:
public void rotate(int[][] matrix) {
int n = matrix.length;
// Step 1: 转置矩阵
for (int i = 0; i < n; i++) {
for (int j = i; j < n; j++) {
// 交换 matrix[i][j] 和 matrix[j][i]
int temp = matrix[i][j];
matrix[i][j] = matrix[j][i];
matrix[j][i] = temp;
}
}
// Step 2: 反转每一行
for (int i = 0; i < n; i++) {
for (int j = 0; j < n / 2; j++) {
// 交换 matrix[i][j] 和 matrix[i][n-1-j]
int temp = matrix[i][j];
matrix[i][j] = matrix[i][n - 1 - j];
matrix[i][n - 1 - j] = temp;
}
}
}
整数数组 nums 按升序排列,数组中的值 互不相同 。
在传递给函数之前,nums 在预先未知的某个下标 k(0 <= k < nums.length)上进行了 旋转,使数组变为 [nums[k], nums[k+1], …, nums[n-1], nums[0], nums[1], …, nums[k-1]](下标 从 0 开始 计数)。例如, [0,1,2,4,5,6,7] 在下标 3 处经旋转后可能变为 [4,5,6,7,0,1,2] 。
给你 旋转后 的数组 nums 和一个整数 target ,如果 nums 中存在这个目标值 target ,则返回它的下标,否则返回 -1 。
示例:
class Solution {
public int search(int[] nums, int target) {
int left = 0;
int right = nums.length - 1;
while (left <= right) {
int mid = left + (right - left) / 2;
// 找到目标值
if (nums[mid] == target) {
return mid;
}
// 判断哪一部分是有序的
if (nums[left] <= nums[mid]) {
// 左侧有序
if (nums[left] <= target && target < nums[mid]) {
right = mid - 1; // 目标在左侧
} else {
left = mid + 1; // 目标在右侧
}
} else {
// 右侧有序
if (nums[mid] < target && target <= nums[right]) {
left = mid + 1; // 目标在右侧
} else {
right = mid - 1; // 目标在左侧
}
}
}
return -1; // 未找到目标值
}
}
已知一个长度为 n 的数组,预先按照升序排列,经由 1 到 n 次 旋转 后,得到输入数组。例如,原数组 nums = [0,1,2,4,5,6,7] 在变化后可能得到:
若旋转 4 次,则可以得到 [4,5,6,7,0,1,2]
若旋转 7 次,则可以得到 [0,1,2,4,5,6,7]
注意,数组 [a[0], a[1], a[2], …, a[n-1]] 旋转一次 的结果为数组 [a[n-1], a[0], a[1], a[2], …, a[n-2]] 。
给你一个元素值 互不相同 的数组 nums ,它原来是一个升序排列的数组,并按上述情形进行了多次旋转。请你找出并返回数组中的 最小元素 。
你必须设计一个时间复杂度为 O(log n) 的算法解决此问题。
示例:
class Solution {
public int findMin(int[] nums) {
int left = 0;
int right = nums.length - 1;
while (left < right) {
int mid = left + (right - left) / 2;
// 比较中间值与右边界值
if (nums[mid] > nums[right]) {
// 最小值在 mid 右侧
left = mid + 1;
} else {
// 最小值在 mid 左侧或 mid 即为最小值
right = mid;
}
}
// 最终 left == right,即为最小值
return nums[left];
}
}
给你一个按照非递减顺序排列的整数数组 nums,和一个目标值 target。请你找出给定目标值在数组中的开始位置和结束位置。
如果数组中不存在目标值 target,返回 [-1, -1]。
你必须设计并实现时间复杂度为 O(log n) 的算法解决此问题。
示例:
class Solution {
private static int findFirstPosition(int[] nums, int target) {