【问题标题】:Count all pairs with given XOR用给定的 XOR 计算所有对
【发布时间】:2019-02-14 05:33:40
【问题描述】:

给定一个大小为 N 的列表。找到满足 A[i] XOR A[j] = x 且 1

输入:list = [3, 6, 8, 10, 15, 50], x = 5

输出:2

解释:(3 ^ 6) = 5 和 (10 ^ 15) = 5

这是我的代码(蛮力):

import itertools
n=int(input())
pairs=0
l=list(map(int,raw_input().split()))
q=[x for x in l if x%2==0]
p=[y for y in l if y%2!=0]
for a, b in itertools.combinations(q, 2):
    if (a^b!=2) and ((a^b)%2==0) and (a!=b):
        pairs+=1
for a, b in itertools.combinations(p, 2):
    if (a^b!=2) and ((a^b)%2==0) and (a!=b):
        pairs+=1
print pairs

如何在 Python 中 O(n) 的复杂性中更有效地做到这一点?

【问题讨论】:

  • @MaharshiRoy 你不需要尝试,只需一组。我不确定你是否理解 trie 是什么。请看下面我的回答
  • 如果你正确地遵循reference,复杂性部分列出了插入的 O(n) 时间。在最坏的情况下,如果同一个桶被连续填满,散列无法提供 O(1)。我有竞争力的编程,因此我多次获得 TLE。 Trie 保证 O(bit-depth) ~ O(1) 插入。因此总体 O(n)
  • 检查这个answer@Messersmith

标签: python xor


【解决方案1】:

观察到如果A[i]^A[j] == x,这意味着A[i]^x == A[j]A[j]^x == A[i]

因此,O(n) 解决方案是遍历关联映射 (dict),其中每个键是来自 A 的项目,每个值是项目的相应计数。然后,对于每个项目,计算A[i]^x,并查看A[i]^x 是否在地图中。如果它在地图中,这意味着A[i]^A[j] == x 代表一些 j。因为我们有一个包含所有等于A[j] 的项目计数的映射,所以对的总数将为num_Ai * num_Aj。请注意,每个元素将被计算两次,因为 XOR 是可交换的(即A[i]^A[j] == A[j]^A[i]),因此我们必须将最终计数除以 2,因为我们已经对每一对进行了双重计算。

def create_count_map(lst):
    result = {}
    for item in lst:
        if item in result:
            result[item] += 1
        else:
            result[item] = 1
    return result

def get_count(lst, x):
    count_map = create_count_map(lst)
    total_pairs = 0
    for item in count_map:
        xor_res = item ^ x
        if xor_res in count_map:
            total_pairs += count_map[xor_res] * count_map[item]
    return total_pairs // 2

print(get_count([3, 6, 8, 10, 15, 50], 5))
print(get_count([1, 3, 1, 3, 1], 2))

输出

2
6

根据需要。

为什么是 O(n)?

list 转换为dict s.t. dict 包含列表中每个项目的计数是 O(n) 时间。

计算item ^ x是O(1)时间,计算这个结果是否在dict也是O(1)时间。 dict 密钥访问也是 O(1),两个元素相乘也是如此。我们做了 n 次,因此循环的时间为 O(n)。

O(n) + O(n) 减少到 O(n) 时间。

编辑以正确处理重复。

【讨论】:

  • 如果有重复,此解决方案将不起作用。示例:如果 l=[1,3,1,3,1] 且 x=2,则所需的输出应该是 6,但它会给出 1 作为输出。
  • 好收获。我认为这个 idea 将适用于重复项,但您必须将set 修改为dict,其中dict 中的每个项目都指向有多少重复项输入列表。以后有机会我会更新的
  • 如果你能更新它真的会很有帮助,谢谢
  • @MaxDaen 好的,看来您确实想要更新。更新! HTH。
  • 非常感谢! :)
【解决方案2】:

接受的答案没有给出 X=0 的正确结果。此代码处理那个微小的错误。您也可以对其进行修改以获取其他值的答案。

def calculate(a) :

# Finding the maximum of the array
maximum = max(a)

# Creating frequency array
# With initial value 0
frequency = [0 for x in range(maximum + 1)]

# Traversing through the array 
for i in a :

    # Counting frequency
    frequency[i] += 1

answer = 0

# Traversing through the frequency array
for i in frequency :

    # Calculating answer
    answer = answer + i * (i - 1) // 2

return answer

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-06-01
    • 2020-12-31
    • 2021-10-15
    • 1970-01-01
    • 1970-01-01
    • 2019-03-13
    • 2015-10-07
    • 1970-01-01
    相关资源
    最近更新 更多