2016-11-26 2 views
0

Je suis nouveau en informatique scientifique. J'ai un tableau numpy 2D (disons, A) avec la forme comme (11153L, 4218L), le type de données est dtype('uint8'). Maintenant, je veux garder des données à quelques (disons, 10000) positions aléatoires (ligne, col) et remplir le reste avec no-data-value - Comment puis-je faire ceci?Comment garder au hasard des valeurs à un nombre spécifique et remplacer le reste sans données dans le tableau 2d numpy sans rien changer d'autres

Ici, no-data-value provient d'une autre variable environnementale, par ex. my_raster_nodata_values = dsc.noDataValue

+0

Rollback la section de mise à jour que le problème a été résolu? – Divakar

Répondre

2

Vous pouvez utiliser np.random.choice avec l'option arg replace ensemble comme False pour sélectionner des indices uniques pour la taille totale de ce tableau et définir ceux comme no_data_value. Ainsi, une mise en œuvre serait -

a.ravel()[np.random.choice(a.size,a.size-10000,replace=0)] = no_data_value 

Nous pouvons également utiliser np.put pour le rendre plus intuitif, comme si -

np.put(a, np.random.choice(a.size,a.size-10000,replace=0), no_data_value) 

Un échantillon analysé devrait le rendre plus facile à comprendre -

In [94]: a  # Input array 
Out[94]: 
array([[163, 80, 142, 169, 214], 
     [ 7, 59, 102, 104, 234], 
     [ 44, 143, 7, 30, 232], 
     [ 71, 15, 64, 42, 141]]) 

In [95]: no_data_value = 0 # No value specifier 

In [98]: N = 10 # Number of elems to keep 

In [99]: a.ravel()[np.random.choice(a.size,a.size-N,replace=0)] = no_data_value 

In [100]: a 
Out[100]: 
array([[ 0, 0, 142, 0, 0], 
     [ 7, 0, 0, 104, 234], 
     [ 0, 0, 7, 30, 232], 
     [ 71, 0, 64, 0, 141]]) 

Si vous avez déjà un ou plusieurs éléments dans le tableau en entrée égal à no_data_value, nous pourrions vouloir compenser le nombre d'éléments à définir en fonction de ce nombre. Ainsi, pour un tel cas, nous aurions une version modifiée, comme si -

S = a.size - N - (a == no_data_value).sum() 
idx = np.random.choice(np.flatnonzero(a!=no_data_value),S,replace=0) 
a.ravel()[idx] = no_data_value 

run Exemple -

In [65]: a 
Out[65]: 
array([[240, 30, 61, 38, 145], 
     [ 91, 65, 108, 154, 118], 
     [155, 198, 65, 65, 189], 
     [248, 140, 154, 186, 186]]) 

In [66]: no_data_value = 65 # No value specifier 

In [67]: N = 10 # Number of elems to keep 

In [68]: S = a.size - N - (a == no_data_value).sum() 

In [69]: idx = np.random.choice(np.flatnonzero(a!=no_data_value),S,replace=0) 

In [70]: a.ravel()[idx] = no_data_value 

In [71]: a 
Out[71]: 
array([[240, 30, 61, 38, 65], 
     [ 65, 65, 108, 65, 65], 
     [ 65, 198, 65, 65, 65], 
     [248, 140, 154, 186, 65]]) 
+0

assez bien! mais y a-t-il un moyen de ne pas transformer le problème initial de performance en réseau, puisque je devrai travailler avec près de 10000 rasters. Est-ce que 'put' est plus rapide que 'ravel'? – SIslam

+0

@SIslam Vous ne savez pas exactement ce que vous entendez par "transformer le tableau d'origine"? Si par là, vous voulez dire "no_data_value" dans le tableau original, je suppose que c'est la question. Si non, pourriez-vous élaborer? – Divakar

+0

@SIslam Si vous faites référence à 'a.ravel()', ce 'ravel()' est simplement une vue dans le tableau et en tant que tel il n'y a pas de transformation. – Divakar