NumPy для пользователей Matlab
Введение
MATLAB® и NumPy/SciPy имеют много общего. Но есть и много различий. NumPy и SciPy были созданы для наиболее естественной работы с численными и научными вычислениями на Python, а не для того, чтобы быть клонами MATLAB®. Эта страница предназначена для сбора информации о различиях, в основном для помощи опытным пользователям MATLAB® в освоении NumPy и SciPy.
Основные отличия
В MATLAB® базовый тип данных — многомерный массив с плавающей точкой двойной точности. Большинство выражений принимают такие массивы и возвращают такие массивы. Операции над двумерными экземплярами этих массивов разработаны так, чтобы действовать более или менее как матричные операции в линейной алгебре. | В NumPy базовый тип — многомерный |
MATLAB® использует индексирование с 1 (один). Начальный элемент последовательности находится с помощью a(1). См. примечание ИНДЕКСИРОВАНИЕ | Python использует индексирование с 0 (ноль). Начальный элемент последовательности находится с помощью a[0]. |
Язык сценариев MATLAB® был создан для выполнения операций линейной алгебры. Синтаксис для основных матричных операций удобен и понятен, но API для добавления графических интерфейсов и создания полноценных приложений — это скорее дополнение. | NumPy базируется на Python, который изначально был разработан как превосходный универсальный язык программирования. Хотя синтаксис Matlab для некоторых манипуляций с массивами более компактен, чем синтаксис NumPy, NumPy (как расширение Python) может выполнять многие вещи, которые Matlab просто не может, например, правильно обрабатывать стеки матриц. |
В MATLAB® массивы имеют семантику передачи по значению, со схемой ленивой копии-при записи, чтобы предотвратить фактическое создание копий до тех пор, пока они не понадобятся. Операции срезов копируют части массива. | В NumPy массивы имеют семантику передачи по ссылке. Операции срезов представляют собой представления в массиве. |
«Массив» или «матрица»? Какой из них использовать?
Исторически NumPy предоставлял специальный тип матрицы, np.matrix, который является подклассом ndarray, делающим бинарные операции операциями линейной алгебры. Вы можете увидеть его в некоторых существующих кодах вместо np.array. Так какой же из них использовать?
Кратко
Используйте массивы.
- Они являются стандартным типом векторов/матриц/тензоров NumPy. Многие функции NumPy возвращают массивы, а не матрицы.
- Существует четкое различие между поэлементными операциями и операциями линейной алгебры.
- Вы можете иметь стандартные векторы или векторы строк/столбцов, если хотите.
До Python 3.5 единственным недостатком использования типа массива было то, что для умножения (сведения) двух тензоров (скалярное произведение, умножение матрицы на вектор и т. д.) нужно было использовать dot вместо *. С Python 3.5 можно использовать оператор умножения матриц @.
Учитывая вышесказанное, мы планируем в конечном итоге упразднить matrix.
Подробно
NumPy содержит как класс array, так и класс matrix. Класс array предназначен для многомерного массива общего назначения для различных видов численных вычислений, в то время как matrix предназначен для облегчения вычислений линейной алгебры. На практике между ними есть только несколько ключевых различий.
-
Операторы
*и@, функцииdot(), иmultiply():- Для
array, ``*`` означает поэлементное умножение, а ``@`` означает умножение матриц; у них есть связанные функцииmultiply()иdot(). (До Python 3.5 оператор@не существовал, и для умножения матриц нужно было использоватьdot()). - Для
matrix, ``*`` означает умножение матриц, а для поэлементного умножения нужно использовать функциюmultiply().
- Для
-
Обработка векторов (одномерные массивы)
- Для
array, формы векторов 1xN, Nx1 и N — это разные вещи. Такие операции, какA[:,1]возвращают одномерный массив формы N, а не двумерный массив формы Nx1. Транспонирование одномерногоarrayничего не делает. - Для
matrix, одномерные массивы всегда преобразуются в 1xN или Nx1 матрицы (строчные или столбцовые векторы).A[:,1]возвращает двумерную матрицу формы Nx1.
- Для
-
Обработка многомерных массивов (ndim > 2)
-
arrayобъекты могут иметь число измерений > 2; -
matrixобъекты всегда имеют ровно два измерения.
-
-
Удобные атрибуты
-
arrayимеет атрибут .T, который возвращает транспонированную матрицу. -
matrixтакже имеет атрибуты .H, .I и .A, которые возвращают сопряжённую транспонированную, обратную иasarray()матрицы соответственно.
-
-
Удобный конструктор
- Конструктор
arrayпринимает (вложенные) Python последовательности в качестве инициализаторов. Например,array([[1,2,3],[4,5,6]]). - Конструктор
matrixдополнительно принимает удобный строковый инициализатор. Например,matrix("[1 2 3; 4 5 6]").
- Конструктор
Использование каждого из них имеет свои преимущества и недостатки:
-
array-
:)Поэлементное умножение простое:A*B. -
:(Необходимо помнить, что умножение матриц имеет свой оператор,@. -
:)Одномерные массивы можно рассматривать как либо строчные, либо столбцовые векторы.A @ vрассматриваетvкак столбцовый вектор, аv @ Aрассматриваетvкак строчный вектор. Это может сэкономить вам написание большого количества транспонирований. -
:)arrayявляется «стандартным» типом NumPy, поэтому он проходит больше тестов и является типом, который с большей вероятностью будет возвращен сторонним кодом, использующим NumPy. -
:)Хорошо подходит для обработки данных любого числа измерений. -
:)Ближе по семантике к тензорной алгебре, если вы знакомы с ней. -
:)Все операции (*,/,+,-и т. д.) являются поэлементными. -
:(Разряженные матрицы изscipy.sparseне взаимодействуют так же хорошо с массивами.
-
-
matrix-
:\\Поведение больше похоже на поведение матриц в MATLAB®. -
<:(Максимально двумерный. Для хранения трёхмерных данных вам понадобитсяarrayили, возможно, список Python изmatrix. -
<:(Минимально двумерный. Векторов быть не может. Они должны быть преобразованы в матрицы с одним столбцом или одной строкой. -
<:(Посколькуarrayявляется стандартным в NumPy, некоторые функции могут возвращатьarray, даже если вы передадите имmatrixв качестве аргумента. Это не должно происходить с функциями NumPy (если это происходит, это ошибка), но сторонний код, основанный на NumPy, может не соблюдать сохранение типа, как NumPy. -
:)A*B— это умножение матриц, поэтому оно выглядит так же, как вы его записываете в линейной алгебре (для Python >= 3.5 обычные массивы имеют ту же удобство с оператором@). -
<:(Поэлементное умножение требует вызова функцииmultiply(A,B). -
<:(Использование перегрузки операторов немного нелогично:*не работает поэлементно, но/работает. - Взаимодействие с
scipy.sparseнемного чище.
-
Поэтому использование array гораздо предпочтительнее. Действительно, мы планируем в конечном итоге упразднить matrix.
Таблица приблизительных эквивалентов MATLAB-NumPy
Таблица ниже предоставляет приблизительные эквиваленты для некоторых распространённых выражений MATLAB®. Это не точные эквиваленты, а скорее подсказки для того, чтобы вы двигались в правильном направлении. Более подробную информацию см. в встроенной документации функций NumPy.
В таблице ниже предполагается, что вы выполнили следующие команды в Python:
from numpy import * import scipy.linalg
Также предполагается ниже, что если в Примечаниях говорится о «матрице», то аргументы являются двумерными сущностями.
Эквиваленты общего назначения
MATLAB | numpy | Примечания |
|---|---|---|
|
| получить справку по функции func |
| узнать, где определена функция func | |
|
| вывести исходный код func (если это не встроенная функция) |
|
| короткое логическое И (встроенный оператор Python); только скалярные аргументы |
|
| короткое логическое ИЛИ (встроенный оператор Python); только скалярные аргументы |
|
| комплексные числа |
|
| Расстояние между 1 и ближайшим числом с плавающей точкой. |
|
| интегрировать ОДУ с методом Рунге-Кутты 4,5 |
|
| интегрировать ОДУ с методом BDF |
Linear Algebra Equivalents
MATLAB | NumPy | Примечания |
|---|---|---|
|
| получение числа измерений массива |
|
| получение числа элементов массива |
|
| получение «размера» матрицы |
|
| получение числа элементов n-го измерения массива |
|
| матричная константа 2x3 |
|
| создание матрицы из блоков |
|
| доступ к последнему элементу в матрице 1xn |
|
| доступ к элементу во второй строке, пятом столбце |
|
| вся вторая строка |
|
| первые пять строк |
|
| последние пять строк |
|
| строки с первого по третий и столбцы с пятого по девятый |
|
| строки 2, 4 и 5 и столбцы 1 и 3. Это позволяет изменять матрицу и не требует обычного среза. |
|
| каждая вторая строка |
|
| каждая вторая строка |
|
|
|
|
|
|
|
| транспонирование |
|
| сопряжённое транспонирование |
|
| умножение матриц |
|
| элементное умножение |
|
| элементное деление |
|
| элементное возведение в степень |
|
| матрица, у которой i,j-й элемент равен (a_ij > 0.5). Результат MATLAB — массив 0 и 1. Результат NumPy — массив логических значений |
|
| поиск индексов, где ( |
|
| извлечение столбцов |
|
| извлечение столбцов |
|
|
|
|
|
|
|
| установка всех значений на одно скалярное значение |
|
| numpy присваивает по ссылке |
|
| слайсы numpy — по ссылке |
|
| преобразование массива в вектор (обратите внимание, что это принудительно создаёт копию). Чтобы получить такой же порядок данных, как в MATLAB, используйте |
|
| создание возрастающего вектора (см. примечание ДИАПАЗОНЫ) |
|
| создание возрастающего вектора (см. примечание ДИАПАЗОНЫ) |
|
| создание столбца-вектора |
|
| двумерный массив 3x4, заполненный нулями с плавающей точкой двойной точности |
|
| трёхмерный массив 3x4x5, заполненный нулями с плавающей точкой двойной точности |
|
| двумерный массив 3x4, заполненный единицами с плавающей точкой двойной точности |
|
| единичная матрица 3x3 |
|
| вектор диагональных элементов |
|
| квадратная диагональная матрица, у которой ненулевые значения являются элементами |
|
| случайная матрица 3x4 |
|
| 4 равномерно распределённых образца между 1 и 3 включительно |
|
| два двумерных массива: один для значений x, другой для значений y |
| наиболее эффективный способ вычисления функций на сетке | |
|
| |
| наиболее эффективный способ вычисления функций на сетке | |
|
| создание m на n копий |
|
| склейка столбцов |
|
| склейка строк |
|
| максимальный элемент |
|
| максимальный элемент каждого столбца матрицы |
|
| максимальный элемент каждой строки матрицы |
|
| сравнение |
|
| норма L2 вектора |
|
| элементный оператор AND (ufunc NumPy) См. примечание LOGICOPS |
|
| элементный оператор OR (ufunc NumPy) См. примечание LOGICOPS |
|
| битовый оператор AND (встроенный в Python и ufunc NumPy) |
|
| битовый оператор OR (встроенный в Python и ufunc NumPy) |
|
| обратная матрица квадратной матрицы |
|
| псевдообратная матрица |
|
| ранг матрицы двумерного массива |
|
| решение уравнения a x = b для x |
| Решить a.T x.T = b.T вместо этого | решение уравнения x a = b для x |
|
| разложение по сингулярным значениям |
|
| факторизация Холецкого матрицы ( |
|
| собственные значения и собственные векторы |
|
| собственные значения и собственные векторы |
| найти | |
|
| QR-разложение |
|
| LU-разложение (примечание: P(Matlab) == transpose(P(numpy)) ) |
|
| Решатель сопряжённых градиентов |
|
| преобразование Фурье |
|
| обратное преобразование Фурье |
|
| сортировка матрицы |
|
| сортировка строк матрицы |
|
| многомерная регрессия |
|
| уменьшение выборки с помощью фильтра низких частот |
|
| |
|
|
Примечания
Подматрица: Присвоение подматрицы может быть выполнено с помощью списков индексов, используя команду ix_. Например, для двумерного массива a, можно сделать следующее: ind=[1,3]; a[np.ix_(ind,ind)]+=100.
Справка: Нет прямого эквивалента команде MATLAB which, но команды help и source обычно отображают имя файла, где находится функция. В Python также есть модуль inspect (выполните import inspect), который предоставляет getfile инструмент, который часто работает.
ИНДЕКСИРОВАНИЕ: MATLAB® использует индексирование, начинающееся с 1, поэтому начальный элемент последовательности имеет индекс 1. Python использует нулевое индексирование, поэтому начальный элемент последовательности имеет индекс 0. Путаница и споры возникают, потому что у каждого есть преимущества и недостатки. Индексирование, начинающееся с 1, соответствует обычному использованию в естественном языке, где «первый» элемент последовательности имеет индекс 1. Нулевое индексирование упрощает индексирование. См. также текст профессора Эдсгера В. Дейкстры.
ДИАПАЗОНЫ: В MATLAB®, 0:5 может использоваться как литерал диапазона, так и индекс «среза» (в скобках); однако в Python конструкции, подобные 0:5, только могут использоваться в качестве индекса среза (в квадратных скобках). Таким образом, был создан несколько необычный объект r_, чтобы предоставить NumPy аналогичный лаконичный механизм построения диапазонов. Обратите внимание, что r_ не вызывается как функция или конструктор, а индексируется с помощью квадратных скобок, что позволяет использовать синтаксис срезов Python в аргументах.
ЛОГИЧЕСКИЕ ОПЕРАТОРЫ: & или | в NumPy – это побитовое И/ИЛИ, а в Matlab & и | – логическое И/ИЛИ. Разница должна быть понятна любому с значительным опытом программирования. Хотя оба могут казаться одинаковыми, есть важные различия. Если бы вы использовали операторы Matlab & или |, вы должны использовать ufuncs NumPy logical_and/logical_or. Заметные различия между операторами & и | Matlab и NumPy:
- Входные данные, не являющиеся логическими {0,1}: на выходе NumPy – побитовое И входных данных. Matlab рассматривает любое ненулевое значение как 1 и возвращает логическое И. Например, (3 & 4) в NumPy – 0, а в Matlab и 3, и 4 считаются логически истинными, и (3 & 4) возвращает 1.
- Приоритет: оператор & NumPy имеет более высокий приоритет, чем логические операторы, такие как < и >; у Matlab – наоборот.
Если вы знаете, что у вас есть логические аргументы, вы можете обойтись операторами NumPy, но будьте осторожны со скобками, например: z = (x > 1) & (x < 2). Отсутствие форм операторов NumPy logical_and и logical_or – это следствие дизайна Python.
RESHAPE и ЛИНЕЙНОЕ ИНДЕКСИРОВАНИЕ: Matlab всегда позволяет обращаться к многомерным массивам с помощью скалярных или линейных индексов, NumPy – нет. Линейные индексы часто используются в программах Matlab, например, find() в матрице возвращает их, в то время как NumPy find работает по-другому. При преобразовании кода Matlab может потребоваться сначала преобразовать матрицу в линейную последовательность, выполнить некоторые операции индексирования, а затем преобразовать обратно. Поскольку reshape (обычно) создаёт представления в одном и том же хранилище, это должно быть довольно эффективным. Обратите внимание, что порядок сканирования, используемый reshape в NumPy, по умолчанию имеет порядок «C», тогда как Matlab использует порядок Fortran. Если вы просто переходите к линейной последовательности и обратно, это не имеет значения. Но если вы переходите от кода Matlab, который полагается на порядок сканирования, то этот код Matlab: z = reshape(x,3,4); должен стать z = x.reshape(3,4,order=’F’).copy() в NumPy.
Настройка среды
В MATLAB® основным инструментом для настройки среды является изменение пути поиска с местоположениями ваших любимых функций. Такие настройки можно поместить в скрипт запуска, который MATLAB выполнит при запуске.
NumPy, или скорее Python, имеют аналогичные возможности.
- Для изменения пути поиска Python, чтобы включить расположения собственных модулей, определите переменную среды
PYTHONPATH. - Для выполнения определённого файла сценария при запуске интерактивного интерпретатора Python определите переменную среды
PYTHONSTARTUP, содержащую имя сценария запуска.
В отличие от MATLAB®, где всё на вашем пути может быть вызвано непосредственно, в Python сначала необходимо выполнить оператор «import», чтобы сделать функции в определённом файле доступными.
Например, вы можете создать скрипт запуска, который выглядит так (Примечание: это просто пример, а не руководство по «лучшим практикам»):
# Make all numpy available via shorter 'np' prefix
import numpy as np
# Make all matlib functions accessible at the top level via M.func()
import numpy.matlib as M
# Make some matlib functions accessible directly at the top level via, e.g. rand(3,3)
from numpy.matlib import rand,zeros,ones,empty,eye
# Define a Hermitian function
def hermitian(A, **kwargs):
return np.transpose(A,**kwargs).conj()
# Make some shortcuts for transpose,hermitian:
# np.transpose(A) --> T(A)
# hermitian(A) --> H(A)
T = np.transpose
H = hermitian
Ссылки
См. http://mathesaurus.sf.net/ для другого перекрёстного справочника MATLAB®/NumPy.
Более подробный список инструментов для научной работы с Python можно найти на странице специализированных программных пакетов.
MATLAB® и SimuLink® являются зарегистрированными товарными знаками компании The MathWorks.
© 2005–2020 NumPy Developers
Licensed under the 3-clause BSD License.
https://numpy.org/doc/1.19/user/numpy-for-matlab-users.html