【问题标题】:Alternative Way to Count Frequency between two lists without count计算两个列表之间没有计数的频率的替代方法
【发布时间】:2017-07-22 09:37:47
【问题描述】:

我创建了以下代码来检查第一个列表与第二个列表的频率,而不使用计数:

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]
frequency = [0,0,0]
for i in range(len(F)):
    for num in N:
        if F[i] == num:
            frequency[i]+=1
print('4 occurs in N', frequency[0], 'times')
print('7 occurs in N', frequency[1], 'times')
print('2 occurs in N', frequency[2], 'times')
print()

代码输出正确:

4 occurs in N 2 times
7 occurs in N 1 times
2 occurs in N 3 times

还有其他方法可以在不使用count 的情况下做到这一点吗?我正在尝试while-loop,但它没有用。任何帮助表示赞赏。

【问题讨论】:

  • “不使用计数”是什么意思?你的意思是序列中的.count(item) 方法?
  • 他的意思是collections.Count类型
  • @Adirio 那是collections.Counter,不是collections.Count
  • 是的,不使用计数或计数器,这只是一个练习,我不在现实世界中使用它,只是为了学习替代方法
  • 是的,只是一个错字,我仍然认为他指的是它。

标签: python list while-loop


【解决方案1】:

您可以使用 set 以高性能实现这一目标。

from collections import defaultdict

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]

set_f = set(F)
freq = defaultdict(int)

for num in N:
    if num in set_f:
       freq[num] += 1

print freq

哒哒!

Out: defaultdict(<type 'int'>, {2: 3, 4: 2, 7: 1})

【讨论】:

  • 很好,这是不使用 Counter 最有效的方法。
  • sets 不需要此功能,为什么不将其保留为list
  • @Adirio:如果您正在执行查找,List 会增加时间复杂度。你需要使用集合。当前示例是一个小场景。但是使用集合而不是列表进行查找是一种值得注意的编程实践。
  • in 对付set (O(1)) 比对付list (O(n)) 快很多
  • 从列表中创建集合会增加开销,而仅靠理论复杂性评估不会混淆。对于查找时间增加的大型列表,这种开销可以忽略不计,但对于这种情况,我非常怀疑开销是否小于改进的查找时间。
【解决方案2】:

您可以使用字典来存储频率:

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]
# Create the initial frequency dictionary
frequency = {}
for item in F:
    frequency[item] = 0

# Count the occurences
for item in N:
    if item in frequency:
        frequency[item] += 1

# Print the occurences
for item in F:
    print('{} occurs in N {} times'.format(item, frequency[item]))
print()

或者,如果您希望它更短:

frequency = dict.fromkeys(N, 0)
for item in N:
    frequency[item] += 1
for item in F:
    print('{} occurs in N {} times'.format(item, frequency[item]))
print()

【讨论】:

  • 我添加了一些优化作为编辑,请接受它们。他们使用 dict 理解进行初始创建,并使用 dict 视图进行打印
  • @Adirio 打印是故意以这种方式完成的,因为它保证打印的顺序正确(dicts 在 3.6 之前是无序的,因此不会被保证)。并且字典理解在那里不必要地复杂,如果应该更短或更快,总是有frequency = dict.fromkeys(F, 0)
  • 这真的很好,只是一个问题你知道为什么while不起作用吗?我正在尝试我的代码的变体,就像你上面的代码一样,问候
  • @Supernova 您的代码不包含while 循环,所以我不能说为什么它不起作用。对不起。
  • 没问题,我只发布了我使用时有效的代码,而它不起作用,问候
【解决方案3】:

您说“不使用 Count”,所以我会说这满足要求:

from collections import  Counter
F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]
counter = Counter(N)
for n in F:
    print(n, 'occurs in N', counter[n], 'times')

【讨论】:

  • 感谢您的建议有没有没有柜台的方法?使用while?
【解决方案4】:

首先,Counter 经过高度测试、高效且是 STL 的一部分,请使用它!

>>> from collections import Counter
>>> Counter([2,3,4,2,5,6,3,2,6,7,3,4])
Counter({2: 3, 3: 3, 4: 2, 6: 2, 5: 1, 7: 1})

其次,您可以构建自己的:

def counter(sequence):
    counts = {}
    for item in sequence:
        counts[item] = counts.get(item, 0) + 1
    return counts

样本输出:

>>> counter([2,3,4,2,5,6,3,2,6,7,3,4])
{2: 3, 3: 3, 4: 2, 5: 1, 6: 2, 7: 1}
>>> counter([4,7,2])
{2: 1, 4: 1, 7: 1}

【讨论】:

  • 我知道柜台很好,我想试试没有柜台,谢谢
  • 你可以自己制作,就像我在第二个例子中展示的那样;)@Supernova
【解决方案5】:

在这篇文章中对来自多个用户的解决方案进行了分组,以便于找到它们。

解决方案 1:collections.Counter

from collections import Counter

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]

times = Counter(N)

for each in F:
    print("{} occurs in N {} times".format(each, times[each]))

解决方案 2:list.count()

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]

for each in F:
    print("{} occurs in N {} times".format(each, N.count(each)))

解决方案 3:for 循环

F = [4,7,2]
N = [2,3,4,2,5,6,3,2,6,7,3,4]

times = {each: 0 for each in F}

for each in N:
    if each in times:
        times[each] += 1

for item, frequency in times.items():
    print("{} occurs in N {} times".format(item, frequency))

【讨论】:

    猜你喜欢
    • 2017-01-27
    • 2020-02-12
    • 2016-09-11
    • 1970-01-01
    • 2017-06-06
    • 2011-03-11
    • 2022-09-30
    • 2020-04-17
    • 1970-01-01
    相关资源
    最近更新 更多