2010-09-16 75 views
6

以下代碼段創建一個「典型的測試陣列」 D類的每個對象的,此數組的目的是在我的程序,以測試的事物的分類。有沒有辦法或者甚至有可能改變數組中的元素類型?指定一個python numpy的陣列

import numpy as np 
import random 
from random import uniform, randrange, choice 

# ... bunch of silly code ... 

def gen_test_array(ua, low_inc, med_inc, num_of_vectors): 
    #typical_array = [ zone_id, ua, inc, veh, pop, hh, with_se, is_cbd, re, se=0, oe] 
    typical_array = np.zeros(shape = (num_of_vectors, 11)) 

    for i in range(0, num_of_vectors): 
    typical_array[i] = [i, int(ua), uniform(low_inc/2, med_inc * 2), uniform(0, 6), 
         randrange(100, 5000), randrange(100, 500), 
         choice([True, False]), choice([True, False]), 
         randrange(100, 5000), randrange(100, 5000), 
         randrange(100, 5000) ] 

    return typical_array 

回答

8

在numpy中這樣做的方法是使用structured array

但是,在很多情況下,你使用的是異構數據,一個簡單的python列表是一個更好的選擇很多。 (或者,雖然這個答案寫得並不廣泛,但pandas.DataFrame對於這種情況絕對是理想的。)

無論如何,上面給出的例子都可以作爲「普通」numpy數組完美工作。您可以在您提供的示例中將所有內容都設置爲浮動狀態。 (一切似乎是一個int,除了浮體兩列...的布爾變量可以容易地表示爲整數。)

儘管如此,爲了說明使用結構化dtypes ...

import numpy as np 

ua = 5 # No idea what "ua" is in your code above... 
low_inc, med_inc = 0.5, 2.0 # Again, no idea what these are... 

num = 100 
num_fields = 11 

# Use more descriptive names than "col1"! I'm just generating the names as placeholders 
dtype = {'names':['col%i'%i for i in range(num_fields)], 
       'formats':2*[np.int] + 2*[np.float] + 2*[np.int] + 2*[np.bool] + 3*[np.int]} 
data = np.zeros(num, dtype=dtype) 

# Being rather verbose... 
data['col0'] = np.arange(num, dtype=np.int) 
data['col1'] = int(ua) * np.ones(num) 
data['col2'] = np.random.uniform(low_inc/2, med_inc * 2, num) 
data['col3'] = np.random.uniform(0, 6, num) 
data['col4'] = np.random.randint(100, 5000, num) 
data['col5'] = np.random.randint(100, 500, num) 
data['col6'] = np.random.randint(0, 2, num).astype(np.bool) 
data['col7'] = np.random.randint(0, 2, num).astype(np.bool) 
data['col8'] = np.random.randint(100, 5000, num) 
data['col9'] = np.random.randint(100, 5000, num) 
data['col10'] = np.random.randint(100, 5000, num) 

print data 

其產生具有11個字段的100個元素的陣列:

array([ (0, 5, 2.0886534380436226, 3.0111285613794276, 3476, 117, False, False, 4704, 4372, 4062), 
     (1, 5, 2.0977199579338115, 1.8687472941590277, 4635, 496, True, False, 4079, 4263, 3196), 
     ... 
     ... 
     (98, 5, 1.1682309811443277, 1.4100766819689299, 1213, 135, False, False, 1250, 2534, 1160), 
     (99, 5, 1.746554619056416, 5.210411489007637, 1387, 352, False, False, 3520, 3772, 3249)], 
     dtype=[('col0', '<i8'), ('col1', '<i8'), ('col2', '<f8'), ('col3', '<f8'), ('col4', '<i8'), ('col5', '<i8'), ('col6', '|b1'), ('col7', '|b1'), ('col8', '<i8'), ('col9', '<i8'), ('col10', '<i8')]) 
4

引用第1章的the NumPy reference:

NumPy provides an N-dimensional array type, the ndarray, which describes a collection of 「items」 of the same type. 

第一行,以便在陣列中的每個成員必須是相同的類型。與普通的Python列表相比,這裏普遍性的損失是允許對數組進行高速操作的權衡:循環可以在不測試每個成員的類型的情況下運行。

+0

有沒有其他方法可以使用np.array? – dassouki 2010-09-16 14:33:08

+1

你究竟想要做什麼?我認爲numpy可以加速數學運算:矩陣乘法,或者採用大量輸入的餘弦。不知道更多關於你在做什麼,我只能提供一個常規的Python列表。 – mtrw 2010-09-16 14:38:43