按位与三元组问题 | 豆包MarsCode AI刷题

131 阅读2分钟

解题思路细化

  1. 理解按位与操作

    • 按位与操作 & 是对两个数的二进制表示的每一位进行与操作。只有当两个数的对应位都为1时,结果的对应位才为1,否则为0。
    • 因此,nums[i] & nums[j] & nums[k] == 0 意味着这三个数的二进制表示中,每一位上至少有一个数为0。
  2. 数据结构的选择

    • 我们可以使用一个二维数组 andResults 来存储所有可能的 nums[i] & nums[j] 的结果。
    • 然后,我们遍历所有可能的三元组 (i, j, k),检查 andResults[i][j] & nums[k] 是否为0。
  3. 算法步骤

    • Step 1: 计算所有可能的 nums[i] & nums[j] 的结果,并存储在 andResults 数组中。
    • Step 2: 遍历所有可能的三元组 (i, j, k),检查 andResults[i][j] & nums[k] 是否为0,如果是,则计数器加1。
public class Main {
    public static int solution(int[] nums) {
        int n = nums.length;
        int[][] andResults = new int[n][n];
        
        // Step 1: Calculate pairwise AND results
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                andResults[i][j] = nums[i] & nums[j];
            }
        }
        
        // Step 2: Count valid triplets
        int count = 0;
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                for (int k = 0; k < n; k++) {
                    if ((andResults[i][j] & nums[k]) == 0) {
                        count++;
                    }
                }
            }
        }
        
        return count;
    }

    public static void main(String[] args) {
        System.out.println(solution(new int[]{2, 1, 3}) == 12 ? 1 : 0);
        System.out.println(solution(new int[]{0, 2, 5}) == 25 ? 1 : 0);
        System.out.println(solution(new int[]{1, 2, 4}) == 24 ? 1 : 0);
    }
}

关键步骤

  • Step 1: 计算所有可能的 nums[i] & nums[j] 的结果,并存储在 andResults 数组中。
  • Step 2: 遍历所有可能的三元组 (i, j, k),检查 andResults[i][j] & nums[k] 是否为0,如果是,则计数器加1

关键步骤提示

  1. Step 1: 计算所有可能的 nums[i] & nums[j] 的结果,并存储在 andResults 数组中。

    • 这一步的目的是为了减少后续计算的复杂度,因为我们可以预先计算出所有可能的 nums[i] & nums[j] 的结果。
  2. Step 2: 遍历所有可能的三元组 (i, j, k),检查 andResults[i][j] & nums[k] 是否为0,如果是,则计数器加1。

    • 这一步的目的是找到所有满足条件的三元组。我们可以通过遍历所有可能的三元组来实现这一点。

优化建议

  • 当前的算法时间复杂度为 O(n^3),对于较大的数组可能会比较慢。可以考虑使用位运算的特性来优化,例如使用位掩码来快速判断是否存在满足条件的三元组。