Как перемешать массив неявных пар?

1

Я пытаюсь сделать перетасовку пар в массиве изображений, и для меня это немного сложно.

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

[[1_1],[1_2],[1_3],[1_4],[1_5],[1_6],[2_1],[2_2],[2_3],[2_4],[2_5],[2_6],[3_1],[3_2],[3_3],[3_4],[3_5],[3_6]]

И так далее, это всего лишь минимальный пример из трех последовательностей, каждый из которых имеет 6 кадров.. но чего я хочу достичь в конце, перетасовки последовательных кадров, так что-то вроде этого

[[1_4],[1_5],[2_3],[2_4],[3_5],[3_6],[1_3],[1_4],[1_1],[1_2],[3_2],[3_3],[1_2],[1_3],[3_3],[3_4],[2_1],[2_2] ....]

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

Есть ли способ сделать это?

  • 0
    [1_1] сбивает с толку, вы имеете в виду ['1_1'] ?
  • 0
    Я просто ссылаюсь на первое изображение в первой последовательности ... ничего более - фактически 1_1 - это трехмерный массив (изображение RGB)
Показать ещё 4 комментария
Теги:
arrays
shuffle

2 ответа

2
Лучший ответ

Я работаю над более чистым вложенным списком (недоверяя [1_1]):

L = [['1_1'],['1_2'],['1_3'],['1_4'],['1_5'],['1_6'],['2_1'],['2_2'],['2_3'],['2_4'],['2_5'],['2_6'],['3_1'],['3_2'],['3_3'],['3_4'],['3_5'],['3_6']]

Затем я создаю вложенный список, т.е. Список пар, с пониманием:

S=[[L[z*2+y] for y in range(2)] for z in range(len(L)//2)] # version 1
S=[[L[z+y] for y in range(2)] for z in range(len(L)-1)]    # version 2
S

Обратите внимание, что есть длина /2 неперекрывающиеся пары, но N-1 перекрывающиеся пары (по одной паре для каждой записи, кроме последней).

Обратите внимание, что во всех выводах ниже я вручную добавил новые строки для удобства чтения и четкости.

Выход на этом этапе:

Версия 1, не перекрывающиеся пары:

[[['1_1'], ['1_2']], 
 [['1_3'], ['1_4']],
 [['1_5'], ['1_6']], 
 [['2_1'], ['2_2']],
 [['2_3'], ['2_4']],
 [['2_5'], ['2_6']],
 [['3_1'], ['3_2']],
 [['3_3'], ['3_4']],
 [['3_5'], ['3_6']]]

Версия 2, перекрывающиеся пары:

[[['1_1'], ['1_2']],
 [['1_2'], ['1_3']],
 [['1_3'], ['1_4']],
 [['1_4'], ['1_5']],
 [['1_5'], ['1_6']],
 [['1_6'], ['2_1']],
 [['2_1'], ['2_2']],
 [['2_2'], ['2_3']],
 [['2_3'], ['2_4']],
 [['2_4'], ['2_5']],
 [['2_5'], ['2_6']],
 [['2_6'], ['3_1']],
 [['3_1'], ['3_2']],
 [['3_2'], ['3_3']],
 [['3_3'], ['3_4']],
 [['3_4'], ['3_5']],
 [['3_5'], ['3_6']]]

Затем перетасовать S, который будет только перетасовывать пары внутри S, а не внутри пар, то есть сначала нужно сделать список пар.

import random
random.shuffle(S)
S

Вывод в этот момент, все еще вложен, конечно:

Неперекрывающиеся случайные пары:

[[['3_3'], ['3_4']],
 [['3_1'], ['3_2']],
 [['2_3'], ['2_4']],
 [['3_5'], ['3_6']],
 [['1_1'], ['1_2']],
 [['1_3'], ['1_4']],
 [['2_1'], ['2_2']],
 [['1_5'], ['1_6']],
 [['2_5'], ['2_6']]]

Выходные перекрывающиеся случайные пары:

[[['1_2'], ['1_3']],
 [['2_1'], ['2_2']],
 [['2_4'], ['2_5']],
 [['2_2'], ['2_3']],
 [['1_3'], ['1_4']],
 [['3_4'], ['3_5']],
 [['3_3'], ['3_4']],
 [['3_2'], ['3_3']],
 [['1_6'], ['2_1']],
 [['2_5'], ['2_6']],
 [['2_6'], ['3_1']],
 [['1_4'], ['1_5']],
 [['1_1'], ['1_2']],
 [['2_3'], ['2_4']],
 [['1_5'], ['1_6']],
 [['3_1'], ['3_2']],
 [['3_5'], ['3_6']]]

Возможно, вы можете использовать это для остальной части проекта.
Если не растворить пары

L2=[]
for x in S:
  for y in x:
    L2.append(y)
print(L2)

Выход растворенных неперекрывающихся пар:

[['3_3'], ['3_4'], ['3_1'], ['3_2'], ['2_3'], ['2_4'],
 ['3_5'], ['3_6'], ['1_1'], ['1_2'], ['1_3'], ['1_4'],
 ['2_1'], ['2_2'], ['1_5'], ['1_6'], ['2_5'], ['2_6']]

Выход растворенных перекрывающихся пар:

[['1_2'], ['1_3'], ['2_1'], ['2_2'], ['2_4'], ['2_5'],
 ['2_2'], ['2_3'], ['1_3'], ['1_4'], ['3_4'], ['3_5'],
 ['3_3'], ['3_4'], ['3_2'], ['3_3'], ['1_6'], ['2_1'],
 ['2_5'], ['2_6'], ['2_6'], ['3_1'], ['1_4'], ['1_5'],
 ['1_1'], ['1_2'], ['2_3'], ['2_4'], ['1_5'], ['1_6'],
 ['3_1'], ['3_2'], ['3_5'], ['3_6']]
  • 0
    но это не то, что я хочу точно, здесь вы перетасовали целые последовательности, поэтому, если у меня есть 6 последовательностей из 1-6, то, что вы делаете, будет делать их так, как 1,3,6,4,5, например, что я хочу, чтобы я перетасовал кадры внутри самих последовательностей изображений, как показано в моем примере выше
  • 0
    Нет, это перетасовывает только целые 6 групп, а не внутри, вы можете видеть это в выводах, которые я предоставил.
Показать ещё 10 комментариев
0

Нам потребуется несколько импорта для упрощения:

from functools import reduce
from itertools import groupby
import operator
import random

Предполагая, что у вас есть список:

ar = [['1_1'],['1_2'],['1_3'],['1_4'],['1_5'],['1_6'],['2_1'],['2_2'],['2_3'],['2_4'],['2_5'],['2_6'],['3_1'],['3_2'],['3_3'],['3_4'],['3_5'],['3_6']]

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

groupedbyimage = [list(g[1]) for g in groupby(ar, lambda x: x[0][0])]

Вышеупомянутая лямбда должна быть чем-то еще в вашем случае, чтобы генерировать нахождение правильных групп, когда вы не просто сравниваете первую букву в строке во вложенных списках.

Затем мы можем застегнуть списки изображений сами по себе, сдвинутыми на один:

groupedandpaired = [list(zip(x, x[1:])) for x in groupedbyimage]

Теперь мы можем groupedandpaired список groupedandpaired список pairlist:

pairlist = reduce(operator.concat, groupedandpaired)

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

random.shuffle(pairlist)
result = list(reduce(operator.concat, pairlist))

И распечатывая результат в REPL, мы видим что-то вроде:

>>> result
[['1_5'], ['1_6'], ['2_1'], ['2_2'], ['1_1'], ['1_2'], ['3_2'], 
 ['3_3'], ['2_2'], ['2_3'], ['3_5'], ['3_6'], ['3_1'], ['3_2'], 
 ['1_3'], ['1_4'], ['1_4'], ['1_5'], ['3_4'], ['3_5'], ['3_3'], 
 ['3_4'], ['2_5'], ['2_6'], ['2_3'], ['2_4'], ['1_2'], ['1_3'], 
 ['2_4'], ['2_5']]

Ещё вопросы

Сообщество Overcoder
Наверх
Меню