2016-03-28 46 views
2

假设我有以下二维数组:如何从二维数组中获取字符串值并将其分配给一维数组?

m_array = [['String A', 1, 1.1, 'haha'], 
      ['String B', 2, 0.9, 'haha'], 
      ['String C', 0, 1.1, 'haha'], 
      ['String D', 3, 0.9, 'haha']] 

的事:我想提取0指数值这个多阵列,即“字符串A”,“串B ','String C','String C'并将其存储在一个数组中:s_array动态。

问题:我使用for循环遍历所有值。下面是代码

# create a single dimensional array 
    s_array = [] 
    # Iterator is the length of the m_array. (Which should be 4; 0-index, 1-index, 2-index and 3-index  
    iterator = range(len(m_array)) 

    i_array = 0 

    if(i_array <=iterator): 
     for str_value in m_array[i_array][0]: 
      s_array.append(str_value) 

此时s_array应具有:

s_array['String A', 'String B', 'String C', 'String D']

但它不会。

我认为我的代码的逻辑有问题。但我无法确定问题,有什么想法?

+0

你期望如果(i_array <=迭代器):'做什么? –

回答

2

使用列表理解:

s_array = [sublist[0] for sublist in m_array] 
print s_array 
>>> ['String A', 'String B', 'String C', 'String D'] 
1

您是通过每个项目m_array[i_array][0]迭代和追加每一个项目,而不是附加的整个列表。你并不需要使用索引,但是,因为你可以通过m_array迭代:

s_array = [] 
for array in m_array: 
    s_array.append(array[0]) 

当所有一for循环的作用是增加事情的清单,那就是你也许可以使用list comprehension标志:

s_array = [array[0] for array in m_array] 
2

一个非常紧凑的方式做,这是使用内置的zip功能。鉴于

m_array = [['String A', 1, 1.1, 'haha'], 
      ['String B', 2, 0.9, 'haha'], 
      ['String C', 0, 1.1, 'haha'], 
      ['String D', 3, 0.9, 'haha']] 

然后

zip(*m_array) 

回报

[('String A', 'String B', 'String C', 'String D'), (1, 2, 0, 3), (1.1000000000000001, 0.90000000000000002, 1.1000000000000001, 0.90000000000000002), ('haha', 'haha', 'haha', 'haha')] 

这是因为* “图示” 运营商在解压缩的m_array物品和通过每一个作为参数传递给zip。请参阅官方Python教程中的Unpacking Argument Lists

所以我们只需要提取第一个元组并将其转换为列表。

s_array = list(zip(*m_array)[0]) 
print(s_array) 

输出

['String A', 'String B', 'String C', 'String D'] 
+0

基础Python,这是最好的方法! –

+1

@ColonelBeauvel ..为什么你说这是最好的方法?......列表理解怎么样? –

+0

@ColonelBeauvel:谢谢!我猜它比BAH的列表comp要浪费更多的内存; OTOH,它可能(可能)更快,尤其是如果子列表很长,因为'zip'循环发生在C速度,而不是列表comp'for'循环的Python速度。 –

0

正如你可以看到有很多方法。最好的情况是,我认为是list comprehension

一项更有趣的方法是使用mapitemgetter

m_array = [['String A', 1, 1.1, 'haha'], 
      ['String B', 2, 0.9, 'haha'], 
      ['String C', 0, 1.1, 'haha'], 
      ['String D', 3, 0.9, 'haha']] 

from operator import itemgetter 

print(list(map(itemgetter(0), m_array))) 
+1

FWIW,我怀疑OP是使用Python 2(否则他们'将'int'与'range'对象进行比较时会出错)。在Python 2中,'list'调用可以省略,因为Python 2的'map'返回一个'list'而不是一个迭代器。 –

0

我想看到的问题。您正在遍历“字符串A”而不是m_array。 m_array [i_array] [0]是“字符串A”,您不会更改i_array的值。

简单的解决方法:

for sublist in m_array: 
    s_array.append(sublist[0]) 

我很抱歉,如果这没有帮助,但我不能要求澄清什么是你想实现(没有足够的声望)。

0

PM 2RING的答复意见,我做了一些剖析测试它揭示了以下结果:

>>> import timeit 
>>> timeit.timeit('[x[0] for x in m_array]', "m_array = [['String A', 1, 1.1, 'haha'], ['String B', 2, 0.9, 'haha'],['String C', 0, 1.1, 'haha'],['String D', 3, 0.9, 'haha']]",number = 10**6) 
0.3232365940002637 
>>> timeit.timeit('list(zip(*m_array))[0]', "m_array = [['String A', 1, 1.1, 'haha'], ['String B', 2, 0.9, 'haha'],['String C', 0, 1.1, 'haha'],['String D', 3, 0.9, 'haha']]",number = 10**6) 
0.6186811590014258 

注:在我的Ubuntu 14.04箱,联想ThinkPad超极本进行的,与酷睿i7 测试。

相关问题