¿Existe una versión multidimensional de arange / linspace en numpy?


83

Me gustaría una lista de matrices 2d NumPy (x, y), donde cada x está en {-5, -4.5, -4, -3.5, ..., 3.5, 4, 4.5, 5} y lo mismo para y .

Yo podría hacer

x = np.arange(-5, 5.1, 0.5)
y = np.arange(-5, 5.1, 0.5)

y luego iterar a través de todos los pares posibles, pero estoy seguro de que hay una manera mejor ...

Me gustaría algo de vuelta que se parezca a:

[[-5, -5],
 [-5, -4.5],
 [-5, -4],
 ...
 [5, 5]]

pero el orden no importa.


1
¿Tienes una pregunta? Editar: veo la preguntaxy = np.matrix([x, y])
Andy Kubiak

Esto simplemente concatena las dos matrices.
Hilemonstoer

1
Estoy un poco confundido, el "Me gustaría algo parecido a:" y "donde cada x está en {-5, -4.5, -4, -3.5, ..., 3.5, 4, 4.5, 5} y lo mismo para y "no parecen coincidir.
Ciro Santilli 郝海东 冠状 病 六四 事件 法轮功

Respuestas:


78

Puede usarlo np.mgridpara esto, a menudo es más conveniente que np.meshgridporque crea las matrices en un solo paso:

import numpy as np
X,Y = np.mgrid[-5:5.1:0.5, -5:5.1:0.5]

Para una funcionalidad similar a linspace, reemplace el paso (es decir 0.5) con un número complejo cuya magnitud especifica el número de puntos que desea en la serie. Usando esta sintaxis, las mismas matrices que arriba se especifican como:

X, Y = np.mgrid[-5:5:21j, -5:5:21j]

Luego puede crear sus pares como:

xy = np.vstack((X.flatten(), Y.flatten())).T

Como sugirió @ali_m, todo esto se puede hacer en una línea:

xy = np.mgrid[-5:5.1:0.5, -5:5.1:0.5].reshape(2,-1).T

¡La mejor de las suertes!


16
... o como una sola línea,xy = np.mgrid[-5:5.1:0.5, -5:5.1:0.5].reshape(2, -1).T
ali_m

23

Esto es justo lo que busca:

matr = np.linspace((1,2),(10,20),10)

Esto significa:

Para la primera columna; del 1 de (1,2) al 10 de (10,20), ponga los 10 números crecientes.

Para la segunda columna; del 2 de (1,2) al 20 de (10,20), ponga los 10 números crecientes.

Y el resultado será:

[[ 1.  2.]
 [ 2.  4.]
 [ 3.  6.]
 [ 4.  8.]
 [ 5. 10.]
 [ 6. 12.]
 [ 7. 14.]
 [ 8. 16.]
 [ 9. 18.]
 [10. 20.]]

También puede mantener aumentando solo los valores de una columna, por ejemplo, si dice que:

matr = np.linspace((1,2),(1,20),10)

La primera columna será de 1 de (1,2) a 1 de (1,20) por 10 veces lo que significa que permanecerá como 1 y el resultado será:

[[ 1.  2.]
 [ 1.  4.]
 [ 1.  6.]
 [ 1.  8.]
 [ 1. 10.]
 [ 1. 12.]
 [ 1. 14.]
 [ 1. 16.]
 [ 1. 18.]
 [ 1. 20.]]

En numerosas versiones anteriores a la 1.16, esto arrojará un error. ver stackoverflow.com/questions/57269217/…
Techniquab

Esto no es bidimensional.
oulenz

¡también funciona con listas como entradas! Excelente como paso de preprocesamiento para meshgrid
Yuri Feldman

13

Creo que quieres np.meshgrid:

Devuelve matrices de coordenadas de vectores de coordenadas.

Cree matrices de coordenadas ND para evaluaciones vectorizadas de campos escalares / vectoriales ND sobre cuadrículas ND, dadas matrices de coordenadas unidimensionales x1, x2, ..., xn.

import numpy as np
x = np.arange(-5, 5.1, 0.5)
y = np.arange(-5, 5.1, 0.5)
X,Y = np.meshgrid(x,y)

puede convertir eso a su salida deseada con

XY=np.array([X.flatten(),Y.flatten()]).T

print XY
array([[-5. , -5. ],
       [-4.5, -5. ],
       [-4. , -5. ],
       [-3.5, -5. ],
       [-3. , -5. ],
       [-2.5, -5. ],
       ....
       [ 3. ,  5. ],
       [ 3.5,  5. ],
       [ 4. ,  5. ],
       [ 4.5,  5. ],
       [ 5. ,  5. ]])

Esto devuelve dos matrices grandes que creo que todavía necesitaría iterar para obtener la matriz de pares deseada. ¿Me equivoco?
Hilemonstoer

Vea mi edición: puede convertirlo a su matriz deseada con bastante facilidad sin iteración
tmdavison

La iteración casi nunca se requiere en numpy;)
OrangeSherbet

6

Si solo desea iterar a través de pares (y no hacer cálculos en todo el conjunto de puntos a la vez), lo mejor es itertools.productque itere a través de todos los pares posibles:

import itertools

for (xi, yi) in itertools.product(x, y):
    print(xi, yi)

Esto evita generar grandes matrices a través de meshgrid.


5

Podemos utilizar la función de organizar como:

z1 = np.array([np.array(np.arange(1,5)),np.array(np.arange(1,5))])
print(z1)
o/p=> [[1 2 3 4]
       [1 2 3 4]]

np.array(np.arange(?
CristiFati

Esto no es bidimensional.
oulenz

1

No estoy seguro de entender la pregunta: para hacer una lista de matrices NumPy de 2 elementos , esto funciona:

import numpy as np
x = np.arange(-5, 5.1, 0.5)
X, Y = np.meshgrid(x, x)
Liszt = [np.array(thing) for thing in zip(X.flatten(), Y.flatten())] # for python 2.7

zip le da una lista de tuplas y la comprensión de la lista hace el resto.


0

No es una solución súper rápida, pero funciona para cualquier dimensión.

import numpy as np
def linspace_md(v_min,v_max,dim,num):
    output = np.empty( (num**dim,dim)  )
    values = np.linspace(v_min,v_max,num)
    for i in range(output.shape[0]):
        for d in range(dim):
            output[i][d] = values[( i//(dim**d) )%num]
    return output

0

Todavía lo hice con Linspace porque prefiero ceñirme a este comando.

Puede crear como el siguiente formato: np.linspace (np.zeros ( ancho ) [0], np.full ((1, ancho ), - 1) [0], alto )

np.linspace(np.zeros(5)[0],np.full((1,5),-1)[0],5)

Salida de lo siguiente:

array([[ 0.  ,  0.  ,  0.  ,  0.  ,  0.  ],
       [-0.25, -0.25, -0.25, -0.25, -0.25],
       [-0.5 , -0.5 , -0.5 , -0.5 , -0.5 ],
       [-0.75, -0.75, -0.75, -0.75, -0.75],
       [-1.  , -1.  , -1.  , -1.  , -1.  ]])

Agrega .tranpose () y obtienes:

array([[ 0.  , -0.25, -0.5 , -0.75, -1.  ],
      [ 0.  , -0.25, -0.5 , -0.75, -1.  ],
      [ 0.  , -0.25, -0.5 , -0.75, -1.  ],
      [ 0.  , -0.25, -0.5 , -0.75, -1.  ],
      [ 0.  , -0.25, -0.5 , -0.75, -1.  ]])

-1

Basado en este ejemplo, puede hacer cualquier atenuación que desee

def linspace3D(point1,point2,length):
    v1 = np.linspace(point1[0],point2[0],length)
    v2 = np.linspace(point1[1],point2[1],length)
    v3 = np.linspace(point1[2],point2[2],length)
    line = np.zeros(shape=[length,3])
    line[:,0]=v1
    line[:,1]=v2
    line[:,2]=v3
    return line
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.