#python #numpy
#python #numpy
Вопрос:
Допустим, у меня есть массив numpy следующим образом:
arr = np.array([[[1, 7], [5, 1]], [[5, 7], [6, 7]]])
где каждый из самых внутренних подмассивов является элементом. Так, например; [1, 7] и [5, 1] оба считаются элементами.
… и я хотел бы найти все элементы, которые удовлетворяют: [<=5, >=7]. Итак, достоверный результирующий массив для приведенного выше примера будет выглядеть следующим образом:
arr_truthy = [[True, False], [True, False]]
… что касается одного из нижних элементов в arr
первом значении <=5
, а второе — >=7
.
Я могу легко решить эту проблему, выполнив итерацию по каждой из осей в arr
:
for x in range(arr.shape[0]):
for y in range(arr.shape[1]):
# test values, report if true.
.. но этот метод медленный, и я надеюсь, что есть другой numpy
способ сделать это. Я пробовал np.where
, но не могу понять, как выполнить условие с несколькими подэлементами.
Я эффективно пытаюсь протестировать независимое условие для каждого числа в элементах.
Кто-нибудь может указать мне правильное направление?
Ответ №1:
Я бы сделал это так. Инициализируйте вывод в той же форме. Затем просто выполните сравнение этих элементов.
out = np.full(arr.shape,False)
out[:,:,0] = arr[:,:,0] >= 5
out[:,:,1] = arr[:,:,1] >= 8
Вывод:
array([[[False, False],
[ True, False]],
[[ True, True],
[ True, False]]])
РЕДАКТИРОВАТЬ: После нашего редактирования, я думаю, вам просто нужен окончательный np.все вдоль последней оси:
np.all(out, axis=-1)
ВОЗВРАТ:
array([[False, False],
[ True, False]])
Комментарии:
1. Извинения.. Я только что немного обновил свой вопрос.. но ваша логика все равно должна сохраняться. Я проверю это.
Ответ №2:
Вы ищете
(arr[:,:,0] <= 5) amp; (arr[:,:,1] >= 7)
? Вы можете выполнить широковещательное сравнение.
Вывод:
array([[True, False],
[True, False]])
Комментарии:
1. Хотя ваш ответ правильный, вы поставили меня в известность о проблеме с моим вопросом. Я отредактирую его, чтобы уточнить.
2. обновлен ответ @desiguel, можете ли вы проверить, работает ли это?
3. Неплохо. Я проверю это.
Ответ №3:
В вашем примере вторая пара ( [5, 1]
) соответствует вашему правилу (первое значение >= 5, а второе <= 7), но в результате( arr_truthy
) его значение равно False . Мой код работает, если это была ошибка, в противном случае, пожалуйста, уточните условие.
arr = np.array([[[1, 7], [5, 1]], [[5, 6], [6, 7]], [[1, 9], [9, 1]]])
# Create True/False arrays for the first/second element of the input
first = np.zeros_like(arr, dtype=bool)
first = first.flatten()
first[::2] = 1
first = first.reshape(arr.shape)
second = np.invert(first)
# The actual logic:
out = np.logical_or(np.where(arr >= 5, first, False), np.where(arr <= 7, second, False))
# Both the condition for the first and for the second element of each par has to be meet
out = out.all(axis=-1)
Комментарии:
1. Неплохо. Спасибо за помощь, но два других ответа выглядят так, как будто они делают что-то похожее на ваше, более лаконично, используя сокращение фрагмента массива. На самом деле довольно круто.. сегодня я узнал, как нарезать массивы!