3

我有两个带有值的列表,预期结果是一个元组(a,b),其中ai 值的数量是list1[i] < list2[i],并且b是 i 值的数量 where list1[i] > list2[i](根本不计算等式)。

我有这个解决方案,而且效果很好:

x = (0,0)
for i in range(len(J48)):
    if J48[i] < useAllAttributes7NN[i]:
      x = (x[0]+1,x[1])
    elif J48[i] > useAllAttributes7NN[i]:
        x = (x[0], x[1]+1)

但是,我正在努力提高我的 Python 技能,而且实现它的方式似乎非常非 Python。

什么是实现相同结果的pythonic方法?

仅供参考,这样做是为了实现所需的输入,binom_test()以试图证明两种算法在统计上并不相同。
不过,我不相信这些信息对特定问题有任何附加价值。

4

6 回答 6

5

一种方法是建立一组分数,然后将它们相加。

scores = [ (a < b, a > b) for (a, b) in zip(J48, useAllAttributes7nn) ]
x = (sum( a for (a, _) in scores ), sum( b for (_, b) in scores ))

// Or, as per @agf's suggestion (though I prefer comprehensions to map)...
x = [ sum(s) for s in zip(*scores) ]

另一种是将它们压缩一次,然后分别计算分数:

zipped = zip(J48, useAllAttributes7nn)
x = (sum( a < b for (a, b) in zipped ), sum( a > b for (a, b) in zipped ))

请注意,这在 Python 3 中不起作用(感谢@Darthfett)。

于 2012-04-30T18:49:31.360 回答
4

Just for the sake of fun, solving this problem using complex numbers. Though not Pythonic but quite mathematical :-)

Just think this problem as plotting the result on a two dimensional complex space

result=sum((x < y) + (x > y)*1j for x,y  in zip(list1,list2))
(result.real,result.imag)
于 2012-04-30T19:40:31.920 回答
2
import itertools

x = [0, 0, 0]
for a, b in itertools.izip(J48, useAllAttributes7NN):
    x[cmp(a, b)] += 1

然后取x[0]x[2],因为x[1]计算等式。

另一种方式(必须解析列表两次):

first = sum(1 for a, b in itertools.izip(J48, useAllAttributes7NN) if a > b)
second = sum(1 for a, b in itertools.izip(J48, useAllAttributes7NN) if a < b)
于 2012-04-30T18:48:31.030 回答
2

一个简单的解决方案是:

list1 = range(10)
list2 = reversed(range(10))
x = [0, 0]
for a, b in zip(list1, list2):
    x[0] += 1 if a < b else 0
    x[1] += 1 if a > b else 0
x = tuple(x)

给我们:

(5, 5)

zip()是一次迭代两个列表的最佳方式。如果您使用的是 Python 2.x,您可能出于性能原因想要使用itertools.izip(它像 Python 3.x 的zip().

在您停止更改列表之前,在列表上工作也更容易,因为列表是可变的。

编辑:

使用以下版本的 Python 3 兼容版本cmp

def add_tuples(*args):
   return tuple(sum(z) for z in zip(*args))

add_tuples(*[(1, 0) if a < b else ((0, 1) if a > b else (0, 0)) for a, b in zip(list1, list2)])
于 2012-04-30T18:49:32.670 回答
0
list1 = [1, 3, 7, 15, 22, 27]
list2 = [2, 5, 10, 12, 20, 30]

x = 0
y = 0 
for index, value in enumerate(list1):
    if value < list2[index]:
        x += 1
    elif value > list2[index]:
        y += 1

print (x, y)
于 2012-04-30T19:07:11.180 回答
0

那么,怎么样:

import itertools
def func(list1, list2):
    x,y = 0,0
    for (a,b) in itertools.izip(list1, list2):
      if a > b:
        x += 1
      elif a < b:
        y += 1
    print x,y
于 2012-04-30T18:51:16.063 回答