Подтвердить что ты не робот

Создание массива numpy с последовательностью

Я нахожусь в моей переходной поездке от MATLAB до scipy (+ numpy) + matplotlib. У меня возникают проблемы при реализации некоторых вещей. Я хочу создать простой векторный массив в трех разных частях. В MATLAB я бы сделал что-то вроде:

vector=[0.2,1:60,60.8];

В результате получается одномерный массив из 62 позиций. Я пытаюсь реализовать это, используя scipy. Самое близкое, что я нахожу сейчас:

a=[[0.2],linspace(1,60,60),[60.8]]

Однако это создает список, а не массив, и, следовательно, я не могу преобразовать его в векторный массив. Но тогда, когда я это делаю, я получаю сообщение об ошибке

a=array([[0.2],linspace(1,60,60),[60.8]])
ValueError: setting an array element with a sequence.

Я считаю, что моим основным препятствием является то, что я не могу понять, как перевести эту простую операцию в MATLAB:

a=[1:2:20];

до numpy. Я знаю, как сделать это для доступа к позициям в массиве, хотя не при создании последовательности. Любая помощь будет оценена, спасибо!

4b9b3361

Ответ 1

Well NumPy реализует функцию создания массива MATLAB, вектор, используя две функции вместо одного - каждый неявно указывает конкретную ось, по которой должно происходить конкатенация. Эти функции:

  • r _ (строка-конкатенация) и

  • c_ (по столбцам)


Итак, для вашего примера эквивалент NumPy:

>>> import numpy as NP

>>> v = NP.r_[.2, 1:10, 60.8]

>>> print(v)
     [  0.2   1.    2.    3.    4.    5.    6.    7.    8.    9.   60.8]

Колонка в виде столбца:

>>> NP.c_[.2, 1:10, 60.8]
Обозначение среза

работает как ожидалось [start: stop: step]:

>>> v = NP.r_[.2, 1:25:7, 60.8]

>>> v
  array([  0.2,   1. ,   8. ,  15. ,  22. ,  60.8])

Хотя если мнимое число используется в качестве третьего аргумента, нотация среза ведет себя как linspace:

>>> v = NP.r_[.2, 1:25:7j, 60.8]

>>> v
  array([  0.2,   1. ,   5. ,   9. ,  13. ,  17. ,  21. ,  25. ,  60.8])


В противном случае он ведет себя как arange:

>>> v = NP.r_[.2, 1:25:7, 60.8]

>>> v
  array([  0.2,   1. ,   8. ,  15. ,  22. ,  60.8])

Ответ 2

Вы можете попробовать что-то вроде:

a = np.hstack(([0.2],np.linspace(1,60,60),[60.8]))

Ответ 3

np.concatenate([[.2], linspace(1,60,60), [60.8]])

Ответ 5

Мне как-то нравится идея построения этих сегментированных диапазонов, о которых вы говорили. Если вы используете их много, возможно, небольшая функция, например

import numpy as np

def segrange(*args):
    result = []
    for arg in args:
        if hasattr(arg,'__iter__'):
            result.append(range(*arg))
        else:
            result.append([arg])
    return np.concatenate(result)

который дает вам

>>> segrange(1., (2,5), (5,10,2))
[ 1.  2.  3.  4.  5.  7.  9.]

было бы неплохо иметь. Хотя, я бы, вероятно, пошел на ответ, используя concatenate/hstack.

Ответ 6

если я правильно понимаю matlab, вы можете сделать что-то вроде этого:

a=np.array([0.2]+list(range(1,61))+[60.8])

Но, вероятно, лучший способ... list(range(1,61)) может быть просто range(1,61), если вы используете python 2.X.

Это работает, создавая 3 списка и затем конкатенируя их с помощью оператора +.

Причина, по которой ваша первоначальная попытка не работала, заключается в том, что

a=[ [0.2], np.linspace(1,60,60), [60.8] ] создает список списков - другими словами:

a[0] == [0.2] #another list (length 1)
a[1] == np.linspace(1,60,60) #an array (length 60)
a[2] == [60.8] #another list (length 1)

Функция array ожидает итерабельность, которая является последовательностью или последовательностью последовательностей, которые имеют одинаковую длину.

Ответ 7

Посмотрите np.r_. Это в основном эквивалентно тому, что предложили все остальные, но если вы пришли из Matlab, это немного интуитивно (и если вы исходите из любого другого языка, это немного противоречит интуиции).

В качестве примера vector=[0.2,1:60,60.8]; переводится на:

vector = np.r_[0.2, 1:61, 60.8]

Ответ 8

Просто хочу указать другим людям, идущим с MATLAB на Numpy, чтобы вы могли построить массив np.r_ с двоеточиями, а затем использовать его для индексации

Например, если у вас есть в matlab

arr_ones = ones(10,10)

Или в Numpy

arr_ones = np.ones([10,10])

В Matlab вы можете брать только столбцы с 1 по 5, а также 7:

arr_ones(:,[1:5 7])

Выполнение этого же в Numpy не является (по крайней мере для меня) интуитивным. Это даст вам ошибку "недопустимый синтаксис":

arr_ones[:,[1:5,7]]

Однако это работает:

inds = np.r[1:5,]
arr_ones[:,inds]

Я знаю, что это не технически новый ответ, но использование двоеточия для построения массива при индексировании в матрицу кажется настолько естественным в Matlab, я уверен, что многие люди, которые приходят на эту страницу, захотят это узнать. (Я пришел сюда вместо того, чтобы задавать новый вопрос.)

Ответ 9

Самый простой способ с помощью numpy.repeat() ||| numpy.tile()

a = np.array([1,2,3,4,5])

np.r_[np.repeat(a,3),np.tile(a,3)]