Conditionally add items to a list when defining the list?

Question:

Is there a way to add items to a list conditionally, when defining the list?
Here’s what I mean:

l = [
    Obj(1),
    Obj(2),
    Separator() if USE_SEPARATORS,
    Obj(3),
    Obj(4),
    Obj(5),
    Separator() if USE_SEPARATORS,
    Obj(6)
]

Obviously the above code doesn’t work, but is there a similar way?

Currently I have

l = [item for item in (
        Obj(1),
        Obj(2),
        Separator() if USE_SEPARATORS,
        Obj(3),
        Obj(4),
        Obj(5),
        Separator() if USE_SEPARATORS,
        Obj(6)
) if not isinstance(item, Separator) or USE_SEPARATORS]

But I was wondering if there’s an other way that wouldn’t required looping through the list, since they can be 10 000 items long and the server stops for a quarter second or so when I execute the code.
It’s for a first-person shooter game, so quarter second might actually have an effect on someone dying or living.

Asked By: Markus Meskanen

||

Answers:

I’d just insert them afterwards; lists are mutable after all:

l = [
    HeadObj(1),
    HeadObj(2),
    BodyObj(1),
    BodyObj(2),
    BodyObj(3),
    FooterObj(1)
]
if USE_SEPARATORS:
    l.insert(2, Separator())
    l.insert(6, Separator())
Answered By: Martijn Pieters

I’d add separators and remove them if not needed:

l = [
    Obj(1),
    Obj(2),
    Separator(),
    Obj(3),
    Obj(4),
    Obj(5),
    Separator(),
    Obj(6)]

if not USE_SEPARATORS:
    l = [object for object in l if not isinstance(object, Separator)]
Answered By: Peter Wood

Another approach is to use the splat/unpacking operator to expand an element either to the separator or to nothing:

possible_separator = (Separator(),) if USE_SEPARATORS else ()
l = [
    Obj(1),
    Obj(2),
    *possible_separator,
    Obj(3),
    Obj(4),
    Obj(5),
    *possible_separator,
    Obj(6)
]
Answered By: jamesdlin
l = [
    Obj(1),
    Obj(2),
    *(Separator() for _i in range(1) if USE_SEPARATORS),
    Obj(3),
    Obj(4),
    Obj(5),
    *(Separator() for _i in range(1) if USE_SEPARATORS),
    Obj(6)
]

The idea is to use the list comprehension syntax to construct either a single element list with item ‘Separator()’, if USE_SEPARATORS is True, or an empty list, if USE_SEPARATORS is False, and then unpack it.

Answered By: victorx