迭代两个嵌套的2D列表,其中list2具有list1的行号

时间:2013-09-19 08:32:02

标签: python list loops

我是Python的新手。所以我想用循环来完成这个,而不使用像发电机这样的奇特东西。我有两个2D数组,一个整数数组和另一个字符串数组,如下所示:

  1. 整数2D列表:

    这里,dataset2d [0] [0]是表中的行数,dataset [0] [1]是列数。所以下面的2D列表有6行4列

    dataset2d = [
        [6, 4],
        [0, 0, 0, 1],
        [1, 0, 2, 0],
        [2, 2, 0, 1],
        [1, 1, 1, 0],
        [0, 0, 1, 1],
        [1, 0, 2, 1]
    ]
    
  2. 字符串2D列表:

    partition2d = [
        ['A', '1', '2', '4'],
        ['B', '3', '5'],
        ['C', '6']
    ]
    

    partition[*][0],即第一列是标签。对于A组,1,2和4是我需要从dataset2d中获取的行号并应用公式。所以这意味着我将阅读1,转到dataset2d中的第1行并读取第一列值dataset2d[1][0],然后我将从partition2d读取2,转到数据集2d的第2行并阅读第一列,即dataset2d[2][0]。同样下一个我会读dataset2d[4][0]

    然后我将进行一些计算,得到一个值并将其存储在2D列表中,然后转到dataset2d中的下一列以获取这些行。因此,在此示例中,读取的下一列值将为dataset2d[1][1]dataset2d[2][1]dataset2d[4][1]。然后再做一些计算并为该列获取一个值,存储它。我会这样做,直到我到达dataset2d的最后一列。

    partition2d中的下一行是[B, 3, 5]。所以我将从dataset2d[3][0]dataset2d[5][0]开始。获取该列的值为公式。然后是真实dataset2d [3][1]dataset2d[5][1]等,直到我到达最后一栏。我这样做,直到读取partition2d中的所有行。

  3. 我尝试了什么:

     for partitionRow in partition2d:
            for partitionCol in partitionRow:
                    for colDataset in dataset2d:
                         print dataset2d[partitionCol][colDataset] 
    

    我面临什么问题:

    1. partition2d是一个字符串数组,我需要跳过第一列,其中包含A,B,C等字符。
    2. 我想仅在partition2d中给出的行号中以列为单位迭代datat2d。因此,只有在完成该列之后,colDataset才会增加。
    3. UPDATE1:

      我正在读取文本文件中的内容,2D列表中的数据可能会有所不同,具体取决于文件内容和大小,但file1即dataset2d和file2即partition2d的结构将是相同的。

      Update2:因为Eric询问输出应该是什么样子。

       0.842322 0.94322 0.34232 0.900009    (For A)
       0.642322 0.44322 0.24232 0.800009    (For B)
      

      这只是一个例子,数字是我随机输入的。 因此,第一个数字0.842322是将公式应用于dataset2d的第0列的结果,即数据集2d [parttionCol] [0],对于已考虑行1,2,4的A组。

      第二个数字0.94322是将公式应用于dataset2d第1列的结果,即在考虑了第1,2行的A组中,dataset2d [partitionCol] [1]。

      第三个数字,0.34232是将公式应用于dataset2d第2列的结果,即dataset2d [partitionCol] [2],对于已考虑行1,2的组A.同样,我们得到0.900009。

      第二行中的第一个数字,即0.642322,是将公式应用于dataset2d的第0列,即dataset2d [parttionCol] [0],用于已考虑行3,5的B组。等等。

5 个答案:

答案 0 :(得分:3)

您可以使用Numpy(我希望这不适合您):

import numpy
dataset2D = [ [6, 4], [0, 0, 0, 1], [1, 0, 2, 0], [2, 2, 0, 1], [1, 1, 1, 0], [0, 0, 1, 1], [1, 0, 2, 1] ]
dataset2D_size = dataset2D[0]
dataset2D = numpy.array(dataset2D)
partition2D = [ ['A', '1', '2', '4'], ['B', '3', '5'], ['C', '6'] ]

for partition in partition2D:
    label = partition[0]

    row_indices = [int(i) for i in partition[1:]]

    # Take the specified rows
    rows = dataset2D[row_indices]

    # Iterate the columns (this is the power of Python!)
    for column in zip(*rows):
        # Now, column will contain one column of data from specified row indices
        print column, # Apply your formula here
    print

如果你不想安装Numpy ,这就是你可以做的(实际上这就是你想要的):

dataset2D = [ [6, 4], [0, 0, 0, 1], [1, 0, 2, 0], [2, 2, 0, 1], [1, 1, 1, 0], [0, 0, 1, 1], [1, 0, 2, 1] ]
partition2D = [ ['A', '1', '2', '4'], ['B', '3', '5'], ['C', '6'] ]

dataset2D_size = dataset2D[0]

for partition in partition2D:
    label = partition[0]

    row_indices = [int(i) for i in partition[1:]]

    rows = [dataset2D[row_idx] for row_idx in row_indices]

    for column in zip(*rows):
        print column,
    print

两者都会打印出来:

(0, 1, 1) (0, 0, 1) (0, 2, 1) (1, 0, 0)
(2, 0) (2, 0) (0, 1) (1, 1)
(1,) (0,) (2,) (1,)

第二个代码的说明(没有Numpy)

[dataset2D[row_idx] for row_idx in row_indices]

这基本上是你采取每一行(dataset2D[row_idx])并将它们整理为一个列表。所以这个表达式的结果是一个列表列表(来自指定的行索引)

for column in zip(*rows):

然后zip(*rows)逐列迭代(您想要的那个)。这可以通过获取每一行的第一个元素,然后将它们组合在一起形成tuple。在每次迭代中,结果都存储在变量column中。

然后在for column in zip(*rows):内你已经有了指定行的预期列式迭代元素!

要应用您的公式,只需将print column,更改为您想要的内容。例如,我修改代码以包含行号和列号:

print 'Processing partition %s' % label
for (col_num, column) in enumerate(zip(*rows)):
    print 'Column number: %d' % col_num
    for (row_num, element) in enumerate(column):
        print '[%d,%d]: %d' % (row_indices[row_num], col_num, element)

将导致:

Processing partition A
Column number: 0
[1,0]: 0
[2,0]: 1
[4,0]: 1
Column number: 1
[1,1]: 0
[2,1]: 0
[4,1]: 1
Column number: 2
[1,2]: 0
[2,2]: 2
[4,2]: 1
Column number: 3
[1,3]: 1
[2,3]: 0
[4,3]: 0
Processing partition B
Column number: 0
[3,0]: 2
[5,0]: 0
Column number: 1
[3,1]: 2
[5,1]: 0
Column number: 2
[3,2]: 0
[5,2]: 1
Column number: 3
[3,3]: 1
[5,3]: 1
Processing partition C
Column number: 0
[6,0]: 1
Column number: 1
[6,1]: 0
Column number: 2
[6,3]: 2
Column number: 3
[6,3]: 1

我希望这会有所帮助。

答案 1 :(得分:2)

这是使用迭代器的可扩展解决方案:

def partitions(data, p):
    for partition in p:
        label = partition[0]
        row_indices = partition[1:]
        rows = [dataset2D[row_idx] for row_idx in row_indices]
        columns = zip(*rows)

        yield label, columns

for label, columns in partitions(dataset2D, partitions2d):
    print "Processing", label
    for column in columns:
        print column

答案 2 :(得分:1)

  

partition2d是一个字符串数组,我需要跳过第一列   其中包含A,B,C等字符。

这称为切片:

 for partitionCol in partitionRow[1:]:

上面的代码段会跳过第一列。

 for colDataset in dataset2d:

已经做了你想要的。这里没有像C ++循环那样的结构。虽然你可以用Unpythonic方式做事:

 i=0
 for i in range(len(dataset2d)):
    print dataset2d[partitionCol][i]  
    i=+1

这是一种非常糟糕的做法。对于数组和矩阵,我建议你不要重新发明轮子(也就是Pythonic的东西),看看{ {1}} 即可。特别是在: numpy.loadtxt

答案 3 :(得分:1)

解决您的问题:

  

我面临什么问题:

     
      
  1. partition2d是我需要的字符串数组   跳过包含A,B,C等字符的第一列。
  2.   
  3. 我想   仅在给定的行号中以列为单位迭代dataset2d   partition2d。所以colDataset只有在我完成后才会增加   那个专栏。
  4.   

问题1可以使用切片来解决 - 如果你想从第二个元素迭代partition2d,你只能使用for partitionCol in partitionRow[1:]。这将从第二个元素开始切片到最后一行。

类似于:

 for partitionRow in partition2d:
        for partitionCol in partitionRow[1:]:
                for colDataset in dataset2d:
                    print dataset2d[partitionCol][colDataset]

问题2我不明白你想要什么:)

答案 4 :(得分:1)

设定:

d = [[6,4],[0,0,0,1],[1,0,2,0],[2,2,0,1],[1,1,1,0],[0,0,1,1],[1,0,2,1]]
s = [['A',1,2,4],['B',3,5],['C',6]]

结果列入清单l

l = []
for r in s: #go over each [character,index0,index1,...]
    new_r = [r[0]] #create a new list to values given by indexN. Add in the character by default
    for i,c in enumerate(r[1:]): #go over each indexN. Using enumerate to keep track of what N is. 
        new_r.append(d[c][i]) #i is now the N in indexN. c is the column.
    l.append(new_r) #add that new list to l

导致

>>> l
[['A', 0, 0, 1], ['B', 2, 0], ['C', 1]]

第一次迭代的执行如下:

for r in s:
    #-> r = ['A',1,2,4]

    new_r = [r[0]] #= ['A']

    for i,c in enumerate([r[1:] = [1,2,4])
            #-> i = 0, c = 1
                new_r.append(d[1][i])
            #-> i = 1, c = 2
                #...