tags:

views:

41

answers:

3

I have a interesting problem. I have a list of lists, and I want all except the first element of each list compiled into a regular expression. And then put back into the list. The lists start as strings.

The following code doesn't work. It doesn't raise an error, it just doesn't seem to do anything. I think I have identified the problem. (see below)

Code:

for i in range(len(groups)):
    for j in range(len(groups[i][1:])):
        groups[i][1:][j] = re.compile(groups[i][1:][j])

The problem as I see it is that, while list[1:] = [1,2,3] works, list[1:][1] = 2 does not work. What would an appropriate fix be?

A: 

You should give a more detailed working example to investigate further. How ever, the problem that you are mentioning does not seem to be an issue. It does work. Unless, I have misunderstood something.

>>> a=[1,2,3,4]
>>> a[1:]
[2, 3, 4]
>>> a[1:][0]
2
>>> a[1:][1]
3
pyfunc
Referencing works, assigning does not.
Skyler
+2  A: 
#!/usr/bin/env python

import re

lol = [
    ["unix", ".*", "cool(, eh)?"],
    ["windows", "_*.*", "[wft]*"],
]

# think of `il` as inner list and `ii` as inner item (if you need) ...
print [ ii[:1] + map(re.compile, ii[1:]) for ii in [ il for il in lol ]]

# ... or, since list comprehensions are preferred over `map`
print [ ii[:1] + [re.compile(x) for x in ii[1:]] for ii in [ il for il in lol ]]

Will yield:

[['unix', <_sre.SRE_Pattern object at 0x100559b90>, <_sre.SRE_Pattern object
at 0x10052b870>], ['windows', <_sre.SRE_Pattern object at 0x100590828>,
<_sre.SRE_Pattern object at 0x10049b780>]]
The MYYN
is there any reason this is better than @Amber below?
Skyler
The MYYN
@Skyler: If you're wanting a new list with the changes made, then this solution does that. If you want to modify the list in place, you'll want to stick with your `for` loops. What it really comes down to though is *use whichever is easier for you to read*.
Amber
+1  A: 

Why bother with slicing? Why not just do...

for i in range(len(groups)):
    for j in range(1, len(groups[i])):
        groups[i][j] = re.compile(groups[i][j])

More detailed explanation of your problem:

"Assigning to a slice" in Python doesn't actually create a slice - it just tells the original object to replace a certain range of elements, hence why for instance a[:2] = [1,2,3] works to replaces the first 3 elements of a list.

If you actually create a slice, though, and then try to index into it (a la a[1:][0]), you're actually indexing into a slice object (and then modifying the slice object) rather than touching the original object.

Amber