View on GitHub

SCRATCH PAD

No polish, just pulse

Striver’s SDE Sheet Notes (Day 2: Arrays & Mathematics)


Day 2: Arrays & Mathematics


1. Rotate Matrix (90 Degrees Clockwise)

public void rotate(int[][] matrix) {
    int n = matrix.length;

    // Transpose the matrix
    for (int i = 0; i < n; i++) {
        for (int j = i; j < n; j++) {
            int temp = matrix[i][j];
            matrix[i][j] = matrix[j][i];
            matrix[j][i] = temp;
        }
    }

    // Reverse each row
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < n / 2; j++) {
            int temp = matrix[i][j];
            matrix[i][j] = matrix[i][n - j - 1];
            matrix[i][n - j - 1] = temp;
        }
    }
}


2. Merge Overlapping Intervals

public int[][] merge(int[][] intervals) {
    Arrays.sort(intervals, (a, b) -> a[0] - b[0]);
    List<int[]> merged = new ArrayList<>();

    for (int[] interval : intervals) {
        if (merged.isEmpty() || merged.get(merged.size() - 1)[1] < interval[0]) {
            merged.add(interval);
        } else {
            merged.get(merged.size() - 1)[1] = Math.max(merged.get(merged.size() - 1)[1], interval[1]);
        }
    }

    return merged.toArray(new int[merged.size()][]);
}


3. Merge Two Sorted Arrays Without Extra Space

public void merge(int[] nums1, int m, int[] nums2, int n) {
    int i = m - 1, j = n - 1, k = m + n - 1;

    while (i >= 0 && j >= 0) {
        if (nums1[i] > nums2[j]) {
            nums1[k--] = nums1[i--];
        } else {
            nums1[k--] = nums2[j--];
        }
    }

    while (j >= 0) {
        nums1[k--] = nums2[j--];
    }
}


4. Find the Duplicate Number

public int findDuplicate(int[] nums) {
    int slow = nums[0];
    int fast = nums[0];

    // Detect cycle
    do {
        slow = nums[slow];
        fast = nums[nums[fast]];
    } while (slow != fast);

    // Find the entry point of the cycle
    fast = nums[0];
    while (slow != fast) {
        slow = nums[slow];
        fast = nums[fast];
    }

    return slow;
}


5. Repeat and Missing Number

public int[] findErrorNums(int[] nums) {
    int xor = 0, xor1 = 0, xor0 = 0;
    int n = nums.length;

    for (int num : nums) xor ^= num;
    for (int i = 1; i <= n; i++) xor ^= i;

    int rightmostBit = xor & -xor;
    for (int num : nums) {
        if ((num & rightmostBit) == 0) xor0 ^= num;
        else xor1 ^= num;
    }

    for (int i = 1; i <= n; i++) {
        if ((i & rightmostBit) == 0) xor0 ^= i;
        else xor1 ^= i;
    }

    for (int num : nums) {
        if (num == xor0) return new int[] {xor0, xor1};
    }

    return new int[] {xor1, xor0};
}


6. Inversion of Array (Count Inversions)

public int countInversions(int[] nums) {
    return mergeSort(nums, 0, nums.length - 1);
}

private int mergeSort(int[] nums, int left, int right) {
    if (left >= right) return 0;

    int mid = left + (right - left) / 2;
    int inversions = mergeSort(nums, left, mid) + mergeSort(nums, mid + 1, right);
    inversions += merge(nums, left, mid, right);

    return inversions;
}

private int merge(int[] nums, int left, int mid, int right) {
    int[] temp = new int[right - left + 1];
    int i = left, j = mid + 1, k = 0;
    int inversions = 0;

    while (i <= mid && j <= right) {
        if (nums[i] <= nums[j]) {
            temp[k++] = nums[i++];
        } else {
            temp[k++] = nums[j++];
            inversions += (mid - i + 1);
        }
    }

    while (i <= mid) {
        temp[k++] = nums[i++];
    }

    while (j <= right) {
        temp[k++] = nums[j++];
    }

    for (i = left, k = 0; i <= right; i++, k++) {
        nums[i] = temp[k];
    }

    return inversions;
}

7. Reverse Pairs

public int reversePairs(int[] nums) {
    return mergeSort(nums, 0, nums.length - 1);
}

private int mergeSort(int[] nums, int left, int right) {
    if (left >= right) return 0;

    int mid = left + (right - left) / 2;
    int count = mergeSort(nums, left, mid) + mergeSort(nums, mid + 1, right);
    count += merge(nums, left, mid, right);

    return count;
}

private int merge(int[] nums, int left, int mid, int right) {
    int count = 0;
    int j = mid + 1;

    // Count reverse pairs
    for (int i = left; i <= mid; i++) {
        while (j <= right && nums[i] > 2L * nums[j]) {
            j++;
        }
        count += (j - mid - 1);
    }

    // Merge step
    List<Integer> temp = new ArrayList<>();
    int i = left, k = mid + 1;
    while (i <= mid && k <= right) {
        if (nums[i] <= nums[k]) {
            temp.add(nums[i++]);
        } else {
            temp.add(nums[k++]);
        }
    }

    while (i <= mid) temp.add(nums[i++]);
    while (k <= right) temp.add(nums[k++]);

    for (i = left; i <= right; i++) {
        nums[i] = temp.get(i - left);
    }

    return count;
}