(Title and contents updated after reading Alex's answer)
In general I believe that it's considered bad form (un-Pythonic) for a function to sometimes return an iterable and sometimes a single item depending on its parameters.
For example struct.unpack
always returns a tuple even if it contains only one item.
I'm trying to finalise the API for a module and I have a few functions that can take one or more parameters (via *args
) like this:
a = s.read(10) # reads 10 bits and returns a single item
b, c = s.read(5, 5) # reads 5 bits twice and returns a list of two items.
So it returns a single item if there's only one parameter, otherwise it returns a list. Now I think this is fine and not at all confusing, but I suspect that others may disagree.
The most common use-case for these functions would be to only want a single item returned, so always returning a list (or tuple) feels wrong:
a, = s.read(10) # Prone to bugs when people forget to unpack the object
a = s.read(10)[0] # Ugly and it's not clear only one item is being returned
Another option is to have two functions:
a = s.read(10)
b, c = s.read_list(5, 5)
which is OK, but it clutters up the API and requires the user to remember twice as many functions without adding any value.
So my question is: Is sometimes returning an iterable and sometimes a single item confusing and un-Pythonic? If so what's the best option?
Update: I think the general consensus is that it's very naughty to only return an iterable sometimes. I think that the best option for most cases would be to always return the iterable, even if it contained only one item.
Having said that, for my particular case I think I'll go for the splitting into two functions (read(item)
/ readlist(*items)
), the reasoning being that I think the single item case will happen much more often than the multiple item case, so it makes it easier to use and the API change less problematic for users.
Thanks everyone.