2016-01-25 4 views
1

У меня есть сетка, где столбцы, которые мы можем представлять как ABC, и строки могут быть представлены, например, как x, y, z.Все комбинации в столбце

Может быть несколько строк, которые все относятся к одному типу. Это не относится к столбцам.

Строки того же типа не следует комбинировать или «смешивать». И все сочетания должны быть в порядке ABC, а не CBA или anyhting. Вот пример, который я придумал.

мне нужно распечатать каждую комбинацию (в columnal порядке) в следующей таблице:

 A B C 
    -------------- 
x | 10 20 30 
x | 11 21 31 

y | 40 50 60 
y | 41 51 61 

z | 70 80 90 

Выход должен быть, как это (он не должен выводить шаблон, это только для справки):

(Pattern) (Result) 
Ax Bx Cx {10 20 30} {11 21 31} (notice no mix-combinations on same letter x) 
Ax Bx Cy {10 20 60} {10 20 61} {11 21 60} {11 21 61} 
Ax Bx Cz {10 20 90} {11 21 90} 
Ax By Cx {10 50 30} {10 51 30} {11 50 31} {11 51 31} 
Ax By Cy {10 50 60} {10 51 61} {11 50 60} {11 51 61} 
Ax By Cz {10 50 90} {10 51 90} {11 50 90} {11 51 90} 
Ax Bz Cx {10 80 30} {11 80 31} 
Ax Bz Cy {10 80 60} {10 80 61} {11 80 60} {11 80 61} 
Ax Bz Cz {10 80 90} {11 80 90} 


Ay Bx Cx {40 20 30} {40 21 31} {41 20 30} {41 21 31} 
Ay Bx Cy ... 
Ay Bx Cz ... 
Ay By Cx ... 
Ay By Cy ... 
Ay By Cz ... 
Ay Bz Cx ... 
Ay Bz Cy ... 
Ay Bz Cz ... 

Az Bx Cx ... 
Az Bx Cy ... 
Az Bx Cz ... 
Az By Cx ... 
Az By Cy ... 
Az By Cz ... 
Az Bz Cx ... 
Az Bz Cy ... 
Az Bz Cz {30 60 90} 

У меня есть код Tcl, который я начал делать, но это не так. Это не займет несколько строк одного и того же х у или г во внимание, но вот что я получил до сих пор:

set dl {0 1 2} 
set op {x y z} 

set debug [open "debugloop.txt" "w"] 
set i 0 
set j 0 
set k 0 
set e 0 
set r 0 
set s 0 
set g yes 
while {$g} { 
    puts $debug A[lindex $op $i][lindex $dl $e]B[lindex $op $j][lindex $dl $r]C[lindex $op $k][lindex $dl $s] 
    incr s 
    if {$s > 2} { 
    puts $debug "" 
    incr r 
    set s 0 
    if {$r > 2} { 
     puts $debug "" 
     incr e 
     set r 0 
     if {$e > 2} { 
     puts $debug "" 
     incr k 
     set e 0 
     if {$k > 2} { 
      puts $debug "" 
      incr j 
      set k 0 
      if {$j > 2} { 
      puts $debug "" 
      incr i 
      set j 0 
      if {$i > 2} { 
       set g no 
      } 
      } 
     } 
     } 
    } 
    } 
} 

Кто-нибудь есть лучший способ сделать это, чем ряд HARDCODED вложенных циклов? У меня было много проблем с этим

ответ

1

Есть 2 основных частей вашей проблемы:

  1. Генерирующие все (Pattern) Комбинации
  2. Сохранение данных таким образом, что позволяет вам найдите результат (Результат) для каждой комбинации.

Для первого из них вам необходимо сгенерировать все перестановки с повторением, допустимыми для ваших значений шаблона x, y, z в вашем примере. Для этого есть код для tcl wiki.

В вашем случае порядок важен, {x, y, z} не совпадает с {z, y, x}, поэтому алгоритм должен учитывать это. Вот некоторый код, который использует простой алгоритм для генерации повторяющихся перестановок, он использует идею, что вы можете сгенерировать все перестановки путем подсчета по модулю количества элементов. Количество перестановок растет довольно быстро, посмотрите на то, как рассчитывается permCount!

# Permutaions 
proc NextPerm {perm values} { 

    set result {} 
    set needIncr 1 
    foreach val $perm { 
     if { $needIncr == 1} { 
      set newVal [lindex $values [expr {[lsearch -exact $values $val] + 1}]] 
      if {$newVal != ""} { 
       # New value was found 
       lappend result $newVal 
       set needIncr 0 
      } else { 
       # No next value found so we need to carry 
       lappend result [lindex $values 0] 
      } 
     } else { 
      lappend result $val 
     } 
    } 

    return $result 
} 

set values {x y z} 
set perm {x x x} 

puts $perm 
set permCount [expr {[llength $perm] ** [llength $perm]}] 
for {set i 1} {$i < $permCount} {incr i} { 
    set perm [NextPerm $perm $values] 
    puts $perm 
} 

NB: Я не пытался оптимизировать этот код.

Если значения шаблонов никогда не изменяются, а затем генерируют их самостоятельно, вы можете использовать онлайн-ресурс, например this (есть много других сайтов, если вы выполняете поиск), чтобы генерировать значения и записывать их в вашу программу.

Для 2 я бы посмотрел на сохранение значений в массиве или dict с помощью ключа, который позволяет отменить соответствующие значения.

+0

спасибо, thats kinda, что я пытался сделать с кодом, который я написал, - сначала создайте правильный шаблон. Я проверю вики –

Смежные вопросы