2016-09-15 5 views
1

Извините, что заголовок не очень ясен.Как преобразовать вложенные массивы в группу одноэлементных массивов

Что бы быть лучшим способом для преобразования

[a, [b, c], [d, e, f], g] 

(или другой аналогичной группы вложенных массивов) в

[a, b, d, g], [a, b, e, g], [a, b, f, g], [a, c, d, g], ..., [a, c, f, g] 

?

+0

Это можно сделать просто с помощью рекурсии. Ты это пробовал.Существуют ли ограничения по временным ограничениям или размер исходного массива. – prabodhprakash

+0

Нужно ли работать на любой уровень гнездования? –

+0

@FrankPuffer Да. – MikeEVMM

ответ

1

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

https://stackoverflow.com/a/9878747/1396822.

или итеративной:

Generating all combinations from collections in Smalltalk

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

+0

Дурр, не понимал, что это декартовой продукт. Благодарю. – MikeEVMM

0

Я сделал это в Python, но этот процесс может быть применен ко всему языку программирования, потому что только две петля:

arr = ["a", ["b", "c"], ["d", "e", "f"], "g"] 

first = arr[1] # b, c 
second = arr[2] # d, e, f 


for j in first: 
    for k in second: 
     print(list((arr[0], j, k, arr[-1]))) 
+0

Спасибо за ваш вклад, но я ищу что-то, что работает для любой вложенности - например, алгоритм должен также работать для [[a, b], [c, d, e], f], например. – MikeEVMM

1

Новое решение

Это нерекурсивно решение написано в Smalltalk. Приемник представляет собой набор подпоследовательностей, таких как [a, [b, c], [d, e, f], g]. Для простоты приведенный ниже код предполагает, что все записи в массиве приемника являются массивами, поэтому правильный приемник будет [[a], [b, c], [d, e, f], [g]], а в Smalltalk - #((a) (b c) (d e f) (g)).

1. selections 
2. | selections indexes index | 
3. selections := OrderedCollection new. 
4. indexes := Array new: self size withAll: 1. 
5. [| group | 
6.  group := (1 to: self size) collect: [:i | (self at: i) at: (indexes at: i)]. 
7.  selections add: group. 
8.  index := (1 to: self size) 
      findLast: [:i | (indexes at: i) < (self at: i) size] 
      ifAbsent: nil. 
9.  index notNil] 
10.  whileTrue: [ 
11.   indexes at: index put: (indexes at: index) + 1. 
12.   index + 1 to: self size do: [:i | indexes at: i put: 1]]. 
13. ^selections 

Комментарии

  1. Имя метода
  2. Временная декларация
  3. Инициализировать выходного
  4. Пуск, выбрав первый элемент из каждой подгруппы
  5. ли .. в то время как
  6. Collect один элемент из каждой подгруппы по текущим показателям
  7. держать группу только что созданную
  8. Найти последний индекс, который может быть увеличен
  9. Стоп, если его нет (это будет переход к 13)
  10. Если есть один такой индекс ...
  11. Increment, что индекс
  12. Сбросить все следующие индексы 1 (это будет получить обратно 6)
  13. Ответить с Результат
+0

Спасибо. Я не знаком с smalltalk, не могли бы вы объяснить причину, лежащую в основе кода? – MikeEVMM

+0

@MikeEVMM Посмотрите мои объяснения сейчас и сообщите мне, если вам нужна дополнительная помощь. –

+0

Ничего себе, большое спасибо за вашу тщательность. Хотя ... Я думаю, что это не решение того, что я просил. '[a, [b, c, d], e]' не должно генерировать (с 'm = 2')' [[a, b], [c, d], [e]] ', а скорее '[[a, b, e], [a, c, e], [a, d, e]]'. – MikeEVMM