Ctrl+Enter
Так как листок пишется с нуля, то в нём хватает опечаток, неточностей и ошибок. Если вы заметили опечатку или ошибку, выделите её, нажмите Ctrl+Enter и опишите проблему. Желательно также написать ещё и её решение.Точно также можно поступить, если какой-то кусок текста совсем непонятен. А если вы можете предложить замену некоторой части на гораздо более понятный текст — то будет просто замечательно!
Введение
Текст про то, зачем применяется NumPy и чем он удобен.
Кроме того, крайне рекомендуется переходить на IDE PyCharm (брать отсюда, Community edition).
В нём достаточное количество удобных фич, которые помогут при написании программ.
Основные hot key:
Ctrl+Alt+E — выполнить выделенный код в консоли
Shift+Ctrl+F10 — запустить текущий скрипт целиком в отдельном процессе
После запуска PyCharm нужно выбрать тему оформления, после чего создать новый проект и выбрать для него интерпретатор Anaconda. При первом запуске PyCharm будет достаточно долго строить список имеющихся пакетов для быстрых подсказок, это может занять от 2 до 20 минут в зависимости от шустрости компьютера.
Документация
- Оригинальный tutorial: https://docs.scipy.org/doc/numpy-dev/user/quickstart.html;
- Оглавление документации: https://docs.scipy.org/doc/numpy/reference/index.html;
- Полный список команд: https://docs.scipy.org/doc/numpy/genindex.html;
- Перевод некоторых частей: https://pythonworld.ru/numpy/1.html;
Замечания по вводу-выводу
Каждая программа должна начинаться со строк с импортированием NumPy и настройкой вывода:
import numpy as np np.set_printoptions(precision=4, threshold=np.nan, linewidth=np.nan, suppress=True)
Если на вход в задаче даётся хотя бы один массив, то получать все данные необходимо из файла input.txt
при помощи команды в духе
ar = eval(open('input.txt').read()) N, K, ar = eval(open('input.txt').read()) ar1, ar2 = eval(open('input.txt').read())
При выводе массивов всегда используйте функцию repr
.
Создание массива
# Одномерный массив нулей >>> np.zeros(5) array([ 0., 0., 0., 0., 0.]) # Двумерный массив нулей >>> np.zeros((2, 3)) array([[ 0., 0., 0.], [ 0., 0., 0.]]) # Трёхмерный массив единиц >>> np.ones((2,3,4)) array([[[ 1., 1., 1., 1.], [ 1., 1., 1., 1.], [ 1., 1., 1., 1.]], [[ 1., 1., 1., 1.], [ 1., 1., 1., 1.], [ 1., 1., 1., 1.]]]) # Массив нулей с указанием типа >>> np.zeros(5, dtype=np.int) array([0, 0, 0, 0, 0]) # Массив на основе списка >>> np.array([2,3,1,0]) array([2, 3, 1, 0]) # Массив на основе списка списков >>> np.array([[1,2.0],[0,0],(1+1j,3.)]) array([[ 1.+0.j, 2.+0.j], [ 0.+0.j, 0.+0.j], [ 1.+1.j, 3.+0.j]]) # Арифметическая прогрессия >>> np.arange(10) array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]) # Арифметическая прогрессия с указанием типа >>> np.arange(2, 10, dtype=np.float) array([ 2., 3., 4., 5., 6., 7., 8., 9.]) # Арифметическая прогрессия с нецелой разностью >>> np.arange(2, 3, 0.1) array([ 2. , 2.1, 2.2, 2.3, 2.4, 2.5, 2.6, 2.7, 2.8, 2.9]) # Арифметическая прогрессия с заданным количеством членов >>> np.linspace(1., 4., 6) array([ 1. , 1.6, 2.2, 2.8, 3.4, 4. ])
01: Массив нулей
На вход даётся число n
. Выведите массив нулей из n
строк и 2n
столбцов.
Ввод | Вывод |
---|---|
3 |
array([[ 0., 0., 0., 0., 0., 0.], [ 0., 0., 0., 0., 0., 0.], [ 0., 0., 0., 0., 0., 0.]]) |
Обращения по индексам
>>> x = np.arange(12).reshape(3, 4) array([[ 0, 1, 2, 3], [ 4, 5, 6, 7], [ 8, 9, 10, 11]]) # Координаты указываем через запятую >>> x[1, 2] 6
02: Числа в нулевой строке
На вход даётся числа n
и m
.
Выведите массив размера n
на m
,
в котором в первой строчке (строка с нулевым индектов) идут числа от 0
до m-1
, а остальные числа равны 0
.
Тип элементов массива должен быть np.int8
.
Ввод | Вывод |
---|---|
3 5 |
array([[0, 1, 2, 3, 4], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]], dtype=int8) |
03: Числа на диагонали
На вход даётся число n
.
Выведите массив размера n
на n
,
в котором по диагонали идут числа от 0
до n-1
.
Тип элементов массива должен быть np.int64
.
Ввод | Вывод |
---|---|
4 |
array([[0, 0, 0, 0], [0, 1, 0, 0], [0, 0, 2, 0], [0, 0, 0, 3]], dtype=int64) |
Срезы
В решениях этих задач необходимо обойтись без циклов.>>> x = np.arange(12).reshape(3, 4) array([[ 0, 1, 2, 3], [ 4, 5, 6, 7], [ 8, 9, 10, 11]]) # Любая координата может быть срезом (:, a:b, ::-1, a:b:c) # Строка с индексом 1 >>> x[1, :] array([4, 5, 6, 7]) # Столбец и индексом 2 >>> x[:, 2] array([ 2, 6, 10]) # Строка в обратном порядке >>> x[0, ::-1] array([3, 2, 1, 0])
04: Сбитый прицел
На вход даются числа n
, r
, c
.
Выведите массив размера n
на n
, в котором
в строке r
и столбце c
стоят 1, а остальные числа равны 0.
Тип элементов массива вы должны "угадать" сами.
Ввод | Вывод |
---|---|
5 1 3 |
array([[0, 0, 0, 1, 0], [1, 1, 1, 1, 1], [0, 0, 0, 1, 0], [0, 0, 0, 1, 0], [0, 0, 0, 1, 0]]) |
05: Почётные единицы
На вход даётся число n
. Выведите массив размера n
на n
,
в котором в строках с чётными индексами стоят 1, а в остальных — нули.
Ввод | Вывод |
---|---|
5 |
array([[1, 1, 1, 1, 1], [0, 0, 0, 0, 0], [1, 1, 1, 1, 1], [0, 0, 0, 0, 0], [1, 1, 1, 1, 1]]) |
06: Решето
На вход даются числа n
, m
, r
, c
.
Выведите массив размера n
на m
, в котором
в котором в каждой r
-ой строчке и в каждом c
-ом столбце стоят 0, а остальные элементы равны 1.
Ввод | Вывод |
---|---|
5 11 3 4 |
array([[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1], [0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1]]) |
07: Шахматы единиц
На вход даётся число n
. Выведите массив размера n
на n
,
имеющий вид шахматной доски.
Ввод | Вывод |
---|---|
5 |
array([[1, 0, 1, 0, 1], [0, 1, 0, 1, 0], [1, 0, 1, 0, 1], [0, 1, 0, 1, 0], [1, 0, 1, 0, 1]]) |
Использование списка индексов в срезах
В решениях этих задач необходимо обойтись без циклов.>>> x = np.arange(12).reshape(3, 4) array([[ 0, 1, 2, 3], [ 4, 5, 6, 7], [ 8, 9, 10, 11]]) # Вместо конкретного индекса можно передать набор индексов >>> x[:, [1, 3]] array([[ 1, 3], [ 5, 7], [ 9, 11]]) # Все передаваемые наборы должны быть одинаковой длины >>> x[[0, 1], [1, 3]] array([1, 7]) >>> x[np.arange(3), np.arange(3)] array([ 0, 5, 10])
08: Разлиновка
На вход даётся число n
. В следующей строке идёт несколько чисел. Выведите массив размера n
на n
,
в котором в строках с перечисленными выше индексами стоят 1.
Ввод | Вывод |
---|---|
10 3 4 7 9 |
array([[0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [1, 1, 1, 1, 1, 1, 1, 1, 1, 1], [1, 1, 1, 1, 1, 1, 1, 1, 1, 1], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [1, 1, 1, 1, 1, 1, 1, 1, 1, 1], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [1, 1, 1, 1, 1, 1, 1, 1, 1, 1]]) |
Векторные операции
В решениях этих задач необходимо обойтись без циклов.>>> x = np.arange(12).reshape(2, 6) # Можно ко всем элементам массива прибавлять числа и другие массивы >>> x + 10 array([[10, 11, 12, 13, 14, 15], [16, 17, 18, 19, 20, 21]]) # Можно все элементы массива умножать на числа или поэлементно на другие массивы >>> x * 3 array([[ 0, 3, 6, 9, 12, 15], [18, 21, 24, 27, 30, 33]]) # Если формы массивов не одинаковые, то происходит "размножение" вдоль координат с размерностью 1 # Например к массиву формы (2, 6) прибляем массив формы (6) = (1, 6). # Вдоль координаты 1 (то есть построчно) происходит размножение >>> x + np.array([0, 10, 100, -10, -100, 0]) array([[ 0, 11, 102, -7, -96, 5], [ 6, 17, 108, -1, -90, 11]]) # Например к массиву формы (2, 6) прибляем массив формы (2, 1) # Вдоль координаты 1 (то есть по столбцам) происходит размножение >>> x + np.array([[0], [-100]]) array([[ 0, 1, 2, 3, 4, 5], [-94, -93, -92, -91, -90, -89]]) >>> x + np.array([0, -100]).reshape((2, 1)) array([[ 0, 1, 2, 3, 4, 5], [-94, -93, -92, -91, -90, -89]]) # Можно ко всем элементам массива применять различные функции, в том числе логические >>> np.sqrt(np.abs(x)) array([[ 0. , 1. , 1.4142, 1.7321, 2. , 2.2361], [ 2.4495, 2.6458, 2.8284, 3. , 3.1623, 3.3166]]) >>> x > 3 array([[False, False, False, False, True, True], [ True, True, True, True, True, True]], dtype=bool) >>> (x > 3) & (x < 8) array([[False, False, False, False, True, True], [ True, True, False, False, False, False]], dtype=bool)
09: Скалярное произведение
На вход даются два массива векторов \(v_i\) и \(w_i\). Вычислите их скалярные произведения \((v_i, w_i)\).
Ввод | Вывод |
---|---|
(np.array([[ 9, -3], [ 2, -10], [ 7, 8]]), np.array([[-5, 2], [ 7, -3], [ 2, 1]])) |
array([-51, 44, 22]) |
10: Нормировка
Дан массив действительных чисел. Отнормируйте (X -> aX+b)
его так, чтобы все числа лежали на отрезке [0,1] и значения 0 и 1 принимались.
Гарантируется, что в массиве есть хотя бы два различных числа.
Ввод | Вывод |
---|---|
np.array([[ 0., -8.], [ 9., -4.], [ 1., 4.]]) |
array([[ 0.4706, 0. ], [ 1. , 0.2353], [ 0.5294, 0.7059]]) |
11: Основное тригонометрическое тождество
Дан массив действительных чисел \(x_i\) длины n
.
Выведите массивы: \(\sin x_i\), \(\cos x_i\), \(\sin^2 x_i\), \(\cos^2 x_i\), \(\sin^2 x_i + \cos^2 x_i\),
Ввод | Вывод |
---|---|
np.array([ 5.6594, 14.8314, 11.1459, 5.9925, -9.2026]) |
array([ 5.6594, 14.8314, 11.1459, 5.9925, -9.2026]) array([-0.5841, 0.7686, -0.9887, -0.2866, -0.2204]) array([ 0.8117, -0.6398, 0.1497, 0.9581, -0.9754]) array([ 0.3412, 0.5907, 0.9776, 0.0821, 0.0486]) array([ 0.6588, 0.4093, 0.0224, 0.9179, 0.9514]) array([ 1., 1., 1., 1., 1.]) |
12: Квадратные уравнения
Даны три массива действительных чисел \(a_i, b_i, c_i\) длины n
.
Выведите массив размера (n, 2)
корней квадратных уравнений \(a_i x^2 + b_i x + c_i\).
Гарантируется, что у каждого уравнения есть два корня.
Ввод | Вывод |
---|---|
(np.array([-5, -1, 4, -2, 1]), np.array([70, 8, -8, 24, -9]), np.array([-225, 9, -192, -54, 14])) |
array([[ 5., 9.], [-1., 9.], [ 8., -6.], [ 3., 9.], [ 7., 2.]]) |
Использование массивов bool
в срезах
В решениях этих задач необходимо обойтись без циклов.
>>> x = np.arange(12).reshape(2, 6) # Вместо индекса можно передать массив bool-ов соответствущей длины: брать/не брать >>> x[np.array([True, False]), :] array([[0, 1, 2, 3, 4, 5]]) >>> x[:, np.array([True, True, False, False, False, True])] array([[ 0, 1, 5], [ 6, 7, 11]]) # Соответствующие массивы bool-ов можно получать автоматически >>> x > 3 array([[False, False, False, False, True, True], [ True, True, True, True, True, True]], dtype=bool) >>> x[x > 3] array([ 4, 5, 6, 7, 8, 9, 10, 11]) # Можно использовать логические связки &=and и |=or, но нужно не забывать про скобки >>> (x > 3) & (x < 8) array([[False, False, False, False, True, True], [ True, True, False, False, False, False]], dtype=bool) >>> x[(x > 3) & (x < 8)] array([4, 5, 6, 7])
13: Больше нуля
Дан массив действительных чисел. Выведите массив его положительных элементов.
Ввод | Вывод |
---|---|
np.array([-5, 1, 7, -8, -3, 9, -4, 6, -2, -9]) |
array([1, 7, 9, 6]) |
14: Поменять знак
Дан массив действительных чисел. Поменяйте знак у элементов, значения которых между 3 и 8.
Ввод | Вывод |
---|---|
np.array([ -8, -6, -3, 8, -4, -10, -9, -7, -3, 6]) |
array([ -8, -6, -3, -8, -4, -10, -9, -7, -3, -6]) |
Максимумы и минимумы
>>> x = np.arange(12).reshape(2, 6) # Находить минимумы и максимумы, а также индексы соответствующих элементов бесконечно просто >>> x = np.random.randint(0, 10, 10) >>> x array([8, 2, 8, 3, 4, 8, 9, 9, 3, 1]) >>> x.max(), x.min(), x.argmax(), x.argmin() (9, 1, 6, 9) # Если массив многомерных, то argmax и argmin возвращают не координату в массиве, а номер по порядку >>> x = np.random.randint(0, 10, (2, 6)) >>> x array([[1, 4, 9, 6, 6, 7], [9, 8, 9, 5, 2, 7]]) >>> x.argmax() 2 # Но его можно превратить в координату в массиве >>> np.unravel_index(x.argmax(), x.shape) (0, 2) # А также найти все наборы координат по заданному правилу >>> np.argwhere(x==x.max()) array([[0, 2], [1, 0], [1, 2]], dtype=int64)
15: Заменить все максимумы
Дан массив действительных чисел. Замените все значения, равные максимальному, на -1.
Ввод | Вывод |
---|---|
np.array([4, 8, 7, 5, 1, 6, 1, 1, 8, 5]) |
array([ 4, -1, 7, 5, 1, 6, 1, 1, -1, 5]) |
16: Ближайшее
Дан массив действительных чисел и некоторое число. Найдите ближайшее по модулю к этому числу значение в массиве и его индекс.
В решении нужно обойтись без циклов.
Ввод | Вывод |
---|---|
(np.array([ 0.91, 0.55, 0.87, 0.52, 0.34, 0.69, 0.74]), 0.5) |
0.52 3 |
17: Построчный и постолбцовый максимум
Дан прямоугольный массив действительных чисел.
Выведите массив максимальных значений в каждой строчке, а за ним массив максимальных значений в каждом столбце.
Ввод | Вывод |
---|---|
np.array([[80, 85, 61], [57, 41, 22]]) |
array([85, 57]) array([80, 85, 61]) |
18: Среднее, построчное и постолбцовое среднее
Дан прямоугольный массив действительных чисел X
.
Выведите три массива: массив X
, у которого из каждого элемента вычли
а) среднее арифметическое всех чисел массива X
;
б) среднее арифметическое всех чисел данной строчки массива X
;
в) среднее арифметическое всех чисел данного столбца массива X
;
Выведите среднее арифметическое чисел массива, массив средний значений в каждой строчке, а за ним массив средний значений в каждом столбце.
Ввод | Вывод |
---|---|
array([[7, 3, 2], [6, 8, 4]]) |
array([[ 2., -2., -3.], [ 1., 3., -1.]]) array([[ 3., -1., -2.], [ 0., 2., -2.]]) array([[ 0.5, -2.5, -1. ], [-0.5, 2.5, 1. ]]) |
Сортировка
>>> a = np.array([[1,4],[3,1]]) array([[1, 4], [3, 1]]) >>> np.sort(a) # Сортировка вдоль последней оси (построчно) array([[1, 4], [1, 3]]) >>> np.sort(a, axis=None) # Сортировка "выпрямленного" массива array([1, 1, 3, 4]) >>> np.sort(a, axis=0) # Сортировка вдоль первой оси (по столбцам) array([[1, 1], [3, 4]]) >>> x = np.array([3, 1, 2]) >>> np.argsort(x) array([1, 2, 0], dtype=int64) >>> x[np.argsort(x)] array([1, 2, 3]) >>> x = np.array([[3, 1, 2], [0, 1, 2], [10, 11, 12]]) >>> x array([[ 3, 1, 2], [ 0, 1, 2], [10, 11, 12]]) >>> x[:, np.argsort(x[0, :])] array([[ 1, 2, 3], [ 1, 2, 0], [11, 12, 10]]) >>> x[np.argsort(x[:, 0]), :] array([[ 0, 1, 2], [ 3, 1, 2], [10, 11, 12]])
??: Размер картинки
В файле input.png
сохранена картинка.
Прочитайте её при помощи команды вида
from skimage import io img = io.imread('input.png')Картинка может быть чёрно-белой или цветной. Выведите её размеры: сначала ширину в пикселях, а затем высоту.
Ввод | Вывод |
---|---|
![]() |
30 60 |
![]() |
30 60 |