Emm*_*Gee 15 python performance list-comprehension
假设我们有一个数字列表,l
.我需要计算所有长度为3的元组l
,(l_i,l_j,l_k)
这样l_i
均匀分割l_j
,并l_j
均匀分割l_k
.规定指数i,j,k
有关系i<j<k
即;
如果l=[1,2,3,4,5,6]
,那么元组将是[1,2,6], [1,3,6],[1,2,4]
,所以COUNT
它将是3.
如果l=[1,1,1]
,那么唯一的元组就是[1,1,1]
,所以COUNT
它将是1.
这是我到目前为止所做的,使用列表推导:
def myCOUNT(l):
newlist=[[x,y,z] for x in l for y in l for z in l if (z%y==0 and y%x==0 and l.index(x)<l.index(y) and l.index(y)<l.index(z))]
return len(newlist)
>>>l=[1,2,3,4,5,6]
>>>myCOUNT(l)
3
Run Code Online (Sandbox Code Playgroud)
这样可行,但随着l
时间的延长(并且可能长达2000个元素),所需的时间会增加太多.有没有更快/更好的方法来做到这一点?
use*_*ica 16
我们可以计算中间给定数字的三元组的数量,通过计算该数字在其左边的多少个因子,计算该数字的右边多少倍,并乘以.对任何给定的中间元素执行此操作对于长度为n的列表是O(n),对于所有n个可能的中间元素执行此操作是O(n ^ 2).
def num_triples(l):
total = 0
for mid_i, mid in enumerate(l):
num_left = sum(1 for x in l[:mid_i] if mid % x == 0)
num_right = sum(1 for x in l[mid_i+1:] if x % mid == 0)
total += num_left * num_right
return total
Run Code Online (Sandbox Code Playgroud)
顺便说一下,你问题中的代码实际上并不起作用.它落入了调用的常见新手陷阱,index
而不是enumerate
用于获取迭代索引.岂止是低效的,其实这是错误的,当输入有重复的元素,导致您myCOUNT
到返回0而不是1对[1, 1, 1]
例如输入.