Масштабирование индексов массива reseape [duplicate]

Любой родитель, который существует в момент привязки события, и если ваша страница динамически создавала элементы с помощью кнопки имени класса, вы привязывали бы событие к родительскому, который уже существует

$(document).ready(function(){
  //Particular Parent chield click
  $(".buttons").on("click","button",function(){
    alert("Clicked");
  });  
  
  //Dynamic event bind on button class  
  $(document).on("click",".button",function(){
    alert("Dymamic Clicked");
  });
  $("input").addClass("button");  
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div class="buttons">
  <input type="button" value="1">
  <button>2</button>
  <input type="text">
  <button>3</button>  
  <input type="button" value="5">  
  </div>
<button>6</button>

4
задан ovs 17 February 2017 в 17:11
поделиться

4 ответа

Вот метод, основанный на инициализации -

def create_grid(m,n):
    out = np.empty((m,n,2),dtype=int) #Improvement suggested by @AndrasDeak
    out[...,0] = np.arange(m)[:,None]
    out[...,1] = np.arange(n)
    return out

Пример прогона -

In [47]: create_grid(4,5)
Out[47]: 
array([[[0, 0],
        [0, 1],
        [0, 2],
        [0, 3],
        [0, 4]],

       [[1, 0],
        [1, 1],
        [1, 2],
        [1, 3],
        [1, 4]],

       [[2, 0],
        [2, 1],
        [2, 2],
        [2, 3],
        [2, 4]],

       [[3, 0],
        [3, 1],
        [3, 2],
        [3, 3],
        [3, 4]]])

Тест времени выполнения для всех подходов, опубликованных до сих пор на (4,5) в сетке и больших размерах -

In [111]: %timeit np.moveaxis(np.indices((4,5)), 0, -1)
     ...: %timeit np.mgrid[:4, :5].swapaxes(2, 0).swapaxes(0, 1)
     ...: %timeit np.mgrid[:4,:5].transpose(1,2,0)
     ...: %timeit create_grid(4,5)
     ...: 
100000 loops, best of 3: 11.1 µs per loop
100000 loops, best of 3: 17.1 µs per loop
100000 loops, best of 3: 17 µs per loop
100000 loops, best of 3: 2.51 µs per loop

In [113]: %timeit np.moveaxis(np.indices((400,500)), 0, -1)
     ...: %timeit np.mgrid[:400, :500].swapaxes(2, 0).swapaxes(0, 1)
     ...: %timeit np.mgrid[:400,:500].transpose(1,2,0)
     ...: %timeit create_grid(400,500)
     ...: 
1000 loops, best of 3: 351 µs per loop
1000 loops, best of 3: 1.01 ms per loop
1000 loops, best of 3: 1.03 ms per loop
10000 loops, best of 3: 190 µs per loop
5
ответ дан Divakar 20 August 2018 в 09:44
поделиться
  • 1
    .swapaxes(-1, 0) дает другой выход, поэтому сравнение времени не очень значимо – Eric 17 February 2017 в 17:42
  • 2
    Эта вторая :,: может быть заменена на ..., чтобы соответствовать первой, правильно? – Eric 17 February 2017 в 17:45
  • 3
    @Eric Yup, пришлось исправить это испытание во время выполнения. – Divakar 17 February 2017 в 17:47
  • 4
    @AndrasDeak Yup! Некоторые заметные улучшения, спасибо большое! :) – Divakar 17 February 2017 в 18:46
  • 5
    yay, мой ответ не самый медленный: -D Вероятно, не стоит создавать здесь numba-функцию, но это заманчиво, если это может побить вас. :) – MSeifert 17 February 2017 в 19:13

С этой целью вы можете злоупотреблять numpy.mgrid или meshgrid:

>>> import numpy as np
>>> np.mgrid[:4,:5].transpose(1,2,0)
array([[[0, 0],
        [0, 1],
        [0, 2],
        [0, 3],
        [0, 4]],

       [[1, 0],
        [1, 1],
        [1, 2],
        [1, 3],
        [1, 4]],

       [[2, 0],
        [2, 1],
        [2, 2],
        [2, 3],
        [2, 4]],

       [[3, 0],
        [3, 1],
        [3, 2],
        [3, 3],
        [3, 4]]])
3
ответ дан Andras Deak 20 August 2018 в 09:44
поделиться

Вы можете использовать numpy.mgrid и обменивать его оси:

>>> # assuming a 3x3 array
>>> np.mgrid[:3, :3].swapaxes(-1, 0)
array([[[0, 0],
        [1, 0],
        [2, 0]],

       [[0, 1],
        [1, 1],
        [2, 1]],

       [[0, 2],
        [1, 2],
        [2, 2]]])

Это все еще немного отличается от вашего желаемого массива, поэтому вы можете катить свои оси:

>>> np.mgrid[:3, :3].swapaxes(2, 0).swapaxes(0, 1)
array([[[0, 0],
        [0, 1],
        [0, 2]],

       [[1, 0],
        [1, 1],
        [1, 2]],

       [[2, 0],
        [2, 1],
        [2, 2]]])

Учитывая, что кто-то приурочил результаты, я также хочу представить версию на основе , которая «бьет все»:

import numba as nb
import numpy as np

@nb.njit
def _indexarr(a, b, out):
    for i in range(a):
        for j in range(b):
            out[i, j, 0] = i
            out[i, j, 1] = j
    return out

def indexarr(a, b):
    arr = np.empty([a, b, 2], dtype=int)
    return _indexarr(a, b, arr)

Сроки:

a, b = 400, 500
indexarr(a, b)  # numba needs a warmup run
%timeit indexarr(a, b)                                  # 1000 loops, best of 3: 1.5 ms per loop
%timeit np.mgrid[:a, :b].swapaxes(2, 0).swapaxes(0, 1)  # 100 loops, best of 3: 7.17 ms per loop
%timeit np.mgrid[:a, :b].transpose(1,2,0)               # 100 loops, best of 3: 7.47 ms per loop
%timeit create_grid(a, b)                               # 100 loops, best of 3: 2.26 ms per loop

и на меньшем массиве:

a, b = 4, 5
indexarr(a, b)
%timeit indexarr(a, b)                                 # 100000 loops, best of 3: 13 µs per loop
%timeit np.mgrid[:a, :b].swapaxes(2, 0).swapaxes(0, 1) # 10000 loops, best of 3: 181 µs per loop
%timeit np.mgrid[:a, :b].transpose(1,2,0)              # 10000 loops, best of 3: 182 µs per loop
%timeit create_grid(a, b)                              # 10000 loops, best of 3: 32.3 µs per loop

Как и было обещано, он «бьет все» с точки зрения производительности: -)

3
ответ дан MSeifert 20 August 2018 в 09:44
поделиться
  • 1
    Интересно, что swapaxes является методом, но moveaxis не является – Eric 17 February 2017 в 17:37
  • 2
    С базовым транспозисом: np.mgrid[:4,:5].transpose(1,2,0) – hpaulj 17 February 2017 в 18:27
  • 3
    Ну, никогда не терпит неудачу! Я не думаю, что это справедливо, если сравнивать с NumPy.) – Divakar 17 February 2017 в 19:46
  • 4
    – Paul Panzer 17 February 2017 в 19:52
  • 5
    @PaulPanzer Я думаю, что почти все ответы имеют некоторую проблему с произвольными размерами (особенно для ndim >= 3, не совсем ясно, в каком порядке должны появляться индексы). – MSeifert 17 February 2017 в 20:13

Вы делаете это, потому что вам это нужно или просто для спорта? В первом случае:

np.moveaxis(np.indices((4,5)), 0, -1)

np.indices делает именно то, что предлагает его название. Только он упорядочивает оси по-другому. Поэтому мы перемещаем их с помощью moveaxis

. Поскольку @Eric указывает, что одна привлекательная особенность этого метода заключается в том, что он работает без изменений при произвольном числе измерений:

dims = tuple(np.multiply.reduceat(np.zeros(16,int)+2, np.r_[0, np.sort(np.random.choice(16, np.random.randint(10)))]))
# len(dims) == ?
np.moveaxis(np.indices(dims), 0, -1) # works
7
ответ дан Paul Panzer 20 August 2018 в 09:44
поделиться
  • 1
  • 2
    Или с базовым методом транспонирования: np.indices((4,5)).transpose(1,2,0) – hpaulj 17 February 2017 в 18:24
  • 3
    @hpaulj, как указывает Эрик, moveaxis(..., 0, -1) работает для любого количества измерений. С помощью transpose вы можете оказаться в roll с помощью arange только для настройки осей тасования ;-) – Paul Panzer 17 February 2017 в 18:30
Другие вопросы по тегам:

Похожие вопросы: