-1

I have a list:

s=[[[’A’, ’B’], [’C’]],[[’A’], [’B’]], [[’B’], [’A’]]]

The length of this list is 3, which means I should get 6 different order of this list:

which means the result should be

[[[’A’, ’B’], [’C’]],[[’A’], [’B’]], [[’B’], [’A’]]]
[[[’A’], [’B’]],[[’A’, ’B’], [’C’]], [[’B’], [’A’]]]
[[[’B’], [’A’]],[[’A’], [’B’]],[[’A’, ’B’], [’C’]]]
.....

My code is:

COUNT=0
order = []
def perm(n,begin,end):
    global COUNT
    if begin>=end:
       order.append(n)
       COUNT +=1
    else:
       i=begin
       for num in range(begin,end):
            n[num],n[i]=n[i],n[num]
            perm(n,begin+1,end)
            n[num],n[i]=n[i],n[num]
  return order
  F =  [[['A', 'B'], ['C']],[['A'], ['B']], [['B'], ['A']]]
  perm(F,0,len(F))

But this result is wrong, it returns six times the same list!

Smile
  • 27
  • 5
  • Possible duplicate of [List of lists changes reflected across sublists unexpectedly](https://stackoverflow.com/questions/240178/list-of-lists-changes-reflected-across-sublists-unexpectedly) and [How to clone or copy a list](https://stackoverflow.com/questions/2612802/how-to-clone-or-copy-a-list) – Patrick Artner Mar 02 '19 at 19:01

2 Answers2

0

I can't tell what's wrong with your code, but you may use itertools module from standard library to get expected result:

import itertools

F =  [[['A', 'B'], ['C']],[['A'], ['B']], [['B'], ['A']]]
for item in itertools.permutations(F):
    print(item)

Output:

([['A', 'B'], ['C']], [['A'], ['B']], [['B'], ['A']])
([['A', 'B'], ['C']], [['B'], ['A']], [['A'], ['B']])
([['A'], ['B']], [['A', 'B'], ['C']], [['B'], ['A']])
([['A'], ['B']], [['B'], ['A']], [['A', 'B'], ['C']])
([['B'], ['A']], [['A', 'B'], ['C']], [['A'], ['B']])
([['B'], ['A']], [['A'], ['B']], [['A', 'B'], ['C']]) 
sanyassh
  • 6,892
  • 12
  • 21
  • 48
0

Your problem is that you did not yet grasp how to copy a list of lists. You are only adding the reference n to your order list. References point to data - as soon as you change the data any other reference you create will still point to the same data. And you create a lot by calling perm iteratively on n:

Change your code to:

import copy 

COUNT=0
order = []
def perm(n,begin,end):
    global COUNT
    if begin>=end:
       order.append(copy.deepcopy(n))   # create a deep copy of the data n points to
       COUNT +=1                        # and store it so it does not change if you 
    else:                               # pass n to perm again further down the line
       i=begin
       for num in range(begin,end):
            n[num],n[i]=n[i],n[num]
            perm(n,begin+1,end)
            n[num],n[i]=n[i],n[num]
    return order


F =  [[['A', 'B'], ['C']],[['A'], ['B']], [['B'], ['A']]]
print(perm(F,0,len(F)))

Output:

[[[['A', 'B'], ['C']], [['A'], ['B']],[['B'], ['A']]], 
 [[['A', 'B'], ['C']], [['B'], ['A']], [['A'], ['B']]], 
 [[['A'], ['B']], [['A', 'B'], ['C']], [['B'], ['A']]], 
 [[['A'], ['B']], [['B'], ['A']], [['A', 'B'], ['C']]], 
 [[['B'], ['A']], [['A'], ['B']], [['A', 'B'], ['C']]], 
 [[['B'], ['A']], [['A', 'B'], ['C']], [['A'], ['B']]]]
Patrick Artner
  • 43,256
  • 8
  • 36
  • 57