Как применить словарь с массивом в качестве значения в массиве NumPy - PullRequest
0 голосов
/ 03 октября 2018

Я пытаюсь отобразить этот словарь

dict = {
5: np.array([1,1,1,1,1], dtype='int'),
4: np.array([1,1,1,1,0], dtype='int'),
3: np.array([1,1,1,0,0], dtype='int'),
2: np.array([1,1,0,0,0], dtype='int'),
1: np.array([1,0,0,0,0], dtype='int'),
0: np.array([0,0,0,0,0], dtype='int'),
-1: np.array([-1,0,0,0,0], dtype='int'),
-2: np.array([-1,-1,0,0,0], dtype='int'),
-3: np.array([-1,-1,-1,0,0], dtype='int'),
-4: np.array([-1,-1,-1,-1,0], dtype='int'),
-5: np.array([-1,-1,-1,-1,-1], dtype='int')}

в этом массиве numpy

target
array([[ 2,  0,  2,  0,  0,  3,  0,  0,  1,  0,  0, -2,  4, -2,  0,  0,
        -3, -3, -5,  1,  0,  0,  0,  2],
       [ 4,  4,  3,  2,  0,  0,  0,  1,  0,  0,  0,  0,  0,  0,  0,  0,
         1, -1, -2, -1, -2, -2, -3, -4],...])

Элементами массива numpy являются int32.Как я могу отобразить это?

Ответы [ 4 ]

0 голосов
/ 03 октября 2018

Поскольку ваши ключи в словаре являются смежными, я бы порекомендовал просто использовать массив здесь для производительности, шаблон для создания такого массива очень прост:

mapper = np.stack([i[1] for i in sorted(d.items())])

array([[-1, -1, -1, -1, -1],
       [-1, -1, -1, -1,  0],
       [-1, -1, -1,  0,  0],
       [-1, -1,  0,  0,  0],
       [-1,  0,  0,  0,  0],
       [ 0,  0,  0,  0,  0],
       [ 1,  0,  0,  0,  0],
       [ 1,  1,  0,  0,  0],
       [ 1,  1,  1,  0,  0],
       [ 1,  1,  1,  1,  0],
       [ 1,  1,  1,  1,  1]])

Теперь вам просто нужно немного обновить свои индексы.Общая идея здесь заключается в том, что там, где у вас в настоящее время есть ключ, соответствующий значению в вашем словаре, теперь у вас должно быть значение, соответствующее индексу строки в вашем массиве mapper.Это будет на намного * на 1009 * более производительный вариант, чем использование словаря при работе с большими массивами:

Для вашего текущего массива это просто увеличило каждое значение на 5, и теперь у вас есть векторизованная индексация:

mapper[target+5]

array([[[ 1.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  0.],
        [ 1.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  0.],
        ...
        [ 0.,  0.,  0.,  0.,  0.],
        [ 1.,  1.,  0.,  0.,  0.]],

       [[ 1.,  1.,  1.,  1.,  0.],
        [ 1.,  1.,  1.,  1.,  0.],
        [ 1.,  1.,  1.,  0.,  0.],
        [ 1.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  0.],
        ...
        [-1., -1.,  0.,  0.,  0.],
        [-1.,  0.,  0.,  0.,  0.]]])

Сроки

big_target = np.repeat(target, 10000, axis=0)

In [307]: %%timeit
 ...: mapper = np.stack([i[1] for i in sorted(d.items())])
 ...: mapper[big_target+5]
 ...:
10.5 ms ± 54.2 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

In [309]: %%timeit
     ...: np.array([list(map(d.__getitem__, row)) for row in big_target])
     ...:
368 ms ± 1.31 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

In [311]: %timeit np.array([[d[j] for j in i] for i in big_target])
361 ms ± 4.35 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

Даже с небольшими накладными расходами при создании массиваиз вашего словаря мы рассматриваем ускорение в 35 раз для массива (20000, 24).

0 голосов
/ 03 октября 2018

Вы можете просто использовать понимание вложенного списка:

[[mydict[j] for j in i] for i in target]

Это дает:

[[array([1, 1, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 1, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 1, 1, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([-1, -1,  0,  0,  0]), array([1, 1, 1, 1, 0]), array([-1, -1,  0,  0,  0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([-1, -1, -1,  0,  0]), array([-1, -1, -1,  0,  0]), array([-1, -1, -1, -1, -1]), array([1, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 1, 0, 0, 0])], [array([1, 1, 1, 1, 0]), array([1, 1, 1, 1, 0]), array([1, 1, 1, 0, 0]), array([1, 1, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([0, 0, 0, 0, 0]), array([1, 0, 0, 0, 0]), array([-1,  0,  0,  0,  0]), array([-1, -1,  0,  0,  0]), array([-1,  0,  0,  0,  0]), array([-1, -1,  0,  0,  0]), array([-1, -1,  0,  0,  0]), array([-1, -1, -1,  0,  0]), array([-1, -1, -1, -1,  0])]]

В качестве исключения, избегайте использования dict в качестве имени переменной, оно перезаписываетdict Python встроенный.

0 голосов
/ 03 октября 2018

Вы можете использовать понимание списка и подать его на np.array:

res = np.array([list(map(d.__getitem__, row)) for row in target])

array([[[ 1,  1,  0,  0,  0],
        [ 0,  0,  0,  0,  0],
        [ 1,  1,  0,  0,  0],
        ...
        [ 0,  0,  0,  0,  0],
        [ 0,  0,  0,  0,  0],
        [ 1,  1,  0,  0,  0]],

       [[ 1,  1,  1,  1,  0],
        [ 1,  1,  1,  1,  0],
        [ 1,  1,  1,  0,  0],
        ...
        [-1, -1,  0,  0,  0],
        [-1, -1, -1,  0,  0],
        [-1, -1, -1, -1,  0]]])

Обратите внимание, что словарь был переименован d: не затенять встроенные модули.

0 голосов
/ 03 октября 2018

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

Что-то вроде этого может быть:

new_target = []
for e in target:
    new_target.append(the_dict[e])

new_target = np.array(new_target)

РЕДАКТИРОВАТЬ: Если вам нужно больше измерений, чем 1, то второй цикл будет вариант.

import numpy as np

my_dict = {
     5: np.array([ 1, 1, 1, 1, 1], dtype='int'),
     4: np.array([ 1, 1, 1, 1, 0], dtype='int'),
     3: np.array([ 1, 1, 1, 0, 0], dtype='int'),
     2: np.array([ 1, 1, 0, 0, 0], dtype='int'),
     1: np.array([ 1, 0, 0, 0, 0], dtype='int'),
     0: np.array([ 0, 0, 0, 0, 0], dtype='int'),
    -1: np.array([-1, 0, 0, 0, 0], dtype='int'),
    -2: np.array([-1,-1, 0, 0, 0], dtype='int'),
    -3: np.array([-1,-1,-1, 0, 0], dtype='int'),
    -4: np.array([-1,-1,-1,-1, 0], dtype='int'),
    -5: np.array([-1,-1,-1,-1,-1], dtype='int'),
}

target = np.array([
    [ 2,  0,  2,  0,  0,  3,  0,  0,  1,  0,
      0, -2,  4, -2,  0,  0, -3, -3, -5,  1,
      0,  0,  0,  2],
    [ 4,  4,  3,  2,  0,  0,  0,  1,  0,  0,
      0,  0,  0,  0,  0,  0,  1, -1, -2, -1,
     -2, -2, -3, -4],
])

new_target = []
for num_list in target:
    sub_new_target = []
    print(num_list)
    for n in num_list:
        sub_new_target.append(my_dict[n])
    new_target.append(sub_new_target)

new_target = np.array(new_target)

print(target.shape)
print(target)
print(new_target.shape)
print(new_target)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...