Python 使用给定的XOR对所有对进行计数

Python 使用给定的XOR对所有对进行计数,python,xor,Python,Xor,给定一个大小为N的列表。找到配对数(i,j),使a[i]XOR a[j]=x,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。如果它在地图中,这意味着对于某些j,A[i]^A[j]==x。因为我们有一个包含所有等于a[j]的项目计数的映射,所以对的总数将是num\u Ai*num

给定一个大小为N的列表。找到配对数(i,j),使a[i]XOR a[j]=x,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
。如果它在地图中,这意味着对于某些
j
,A[i]^A[j]==x。因为我们有一个包含所有等于
a[j]
的项目计数的映射,所以对的总数将是
num\u Ai*num\u 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)?

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

计算
项^x
是O(1)时间,计算该结果是否在
dict
中也是O(1)时间
dict
键访问也是O(1),两个元素的乘法也是O(1)。我们做了n次,因此循环的时间是O(n)

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


编辑以正确处理重复项。

接受的答案没有给出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

@MaharshiRoy你不需要试一下,只要一套就行了。我不确定你是否明白trie是什么。请参阅下面我的答案。如果您正确地遵循了,复杂性部分列出了插入时间。在最坏的情况下,如果同一个存储桶连续被填满,哈希无法提供O(1)。我喜欢竞争性编程,因此我多次获得TLE。Trie保证O(位深度)~O(1)插入。因此,总体O(n)检查@MesserSmith如果存在重复项,则该解决方案不起作用。示例:如果l=[1,3,1,3,1]和x=2,所需的输出应该是6,但它会给出1作为输出。捕捉得好。我认为这个想法适用于重复项,但您必须将
集合
修改为
dict
,其中
dict
中的每个项目都指向输入列表中有多少重复项。如果有机会,我会稍后更新如果你能更新的话,我会很有帮助的,thanks@MaxDaen好吧,看来你真的想要更新。更新!嗯。非常感谢!:)
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