1

I am making a function that takes in a string and returns all possibilities of outputs, using the following transformations:

o -> 0  i,l -> 1
z -> 2  e -> 3
a -> 4  s -> 5
b -> 6  t -> 7
b -> 8  g,q -> 9 

For example:

print(transform_digits("Bow"))
['Bow', 'B0w', '6ow', '60w', '8ow', '80w']

Here is the helper function that I use to get a transformation of a string st at an index i:

def position_transform(st,i):
    letter=st[i]
    front = st[:i]
    back=st[(i+1):]
    l=[]
    if (letter=="o" or letter=="O"): l.append(front+"0"+back)
    elif (letter=="z" or letter=="Z"): l.append(front+"2"+back)
    elif (letter=="a" or letter=="A"): l.append(front+"4"+back)
    elif (letter=="b" or letter=="B"):
        l.append(front+"6"+back)
        l.append(front+"8"+back)
    elif (letter=="i" or letter=="I"or letter=="l" or letter =="L"): l.append(front+"1"+back)
    elif (letter=="e" or letter=="E"): l.append(front+"3"+back)
    elif (letter=="s" or letter=="S"): l.append(front+"5"+back)
    elif (letter=="t" or letter=="T"): l.append(front+"7"+back)
    elif (letter=="g" or letter=="G"or letter=="q" or letter =="Q"): l.append(front+"9"+back)
    return l

Here is the main function:

def transform_digits(st):
    l=[]
    l.append(st)
    newl=l[:]
    length=len(st)
    for x in range(0,length):
        for i in l:
            s=position_transform(i,x)
            newl.append(s)
        l=newl[:]
    return l

when I run the main function I get:

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 8, in transform_digits
  File "<stdin>", line 2, in position_transform
IndexError: list index out of range

I'm not exactly sure where this error is. I've tried running position_transform on strings and that seems to work out fine, and my logic for the other functions seems fine, not sure where the index error is.

mech
  • 2,775
  • 5
  • 30
  • 38
Anatoliy Sokolov
  • 347
  • 1
  • 4
  • 10

1 Answers1

0

The issue is newl.append(s). You're appending the result of your position_transform(i,x) to your list, except position_transform returns a list, so you end up with lists inside lists. That means that, down the line, you try to position_transform and pass a list instead of a string. The list only has a few (1-2) items in it, far less than a string would have characters, leading to your IndexError.

If you want to append the contents of a list to another list, use the [1:1] slice, so your assignment would become newl[1:1] = s. So your nested for-loop now looks like this:

for x in range(0,length):
    for i in l:
        s=position_transform(i,x)
        newl[1:1] = s
    l=newl[:]

This makes the program execute fine, as far as I can tell.

In the future, I recommend choosing to use more descriptive variable names, and trying to comment your code as you write it. Otherwise you may end up staring at fucntions that you wrote 5 minutes ago, wondering what's going on in there. Writing maintainable code is very important!

Community
  • 1
  • 1
mech
  • 2,775
  • 5
  • 30
  • 38
  • Yeah obviously I would comment and have better var names if the functions get more complicated, I was used to append combining 2 lists in the previous language I learned, good to know that I have to do it this way. – Anatoliy Sokolov Feb 24 '16 at 18:41
  • Specially when asking questions on Stack Overflow, the more readable your code is, the more likely you are to get help (and quicker) :) – mech Feb 24 '16 at 18:42
  • do you mean `newl.extend(s)`? – Aprillion Feb 24 '16 at 19:39
  • Sure, but his code uses a lot of slicing (such as `[:]`, `[:i]`, ...), so I used the slice notation equivalent to `extend` to keep it consistent. – mech Feb 24 '16 at 19:53
  • 1
    good point, ill make my code more readable when I post on here – Anatoliy Sokolov Feb 24 '16 at 19:56
  • oh ok so I can use extend as well, also good to know, the previous language I used append for you could write list @ list where @ is append and it combines them – Anatoliy Sokolov Feb 24 '16 at 19:58