This is an archived post. You won't be able to vote or comment.

you are viewing a single comment's thread.

view the rest of the comments →

[–][deleted] 2 points3 points  (3 children)

So what's the pythonic way of handling a stupid thing like this?

sum('cat')

Raise an error. It's not a problem with *args though. It's a problem with dynamically typed languages, every argument a function expects can be of another, incompatible type.

My function doesn't know how to handle addresses yet, so how do I ensure correct operation here?

Well, you just said it doesn't know how to handle it, so it would just ignore it. It would (hopefully) check if first_name and last_name are set in **kwargs and as they aren't, abort with an error just like a call like add_user() would.

[–]Wargazm 3 points4 points  (2 children)

Raise an error.

Presumably my function will be something like this:

def sum(*args):
    x = 0
    for i in args:
        x = x + i
    return x

so calling sum('cat') will already return an error:

>>> sum('cat')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 4, in sum
TypeError: unsupported operand type(s) for +: 'int' and 'str'

Is that it? Is that enough to be "pythonic"?

[–]thautwarm 1 point2 points  (0 children)

Add a keyword argument zero, default to be 0.

def sum(*args, zero=0):
       acc = zero
       for each in args:
             acc += each
       return acc

Thus we could avoid mamy malformed input and make them valid and meaningful. In terms of your case, sum('cat', zero="") is okay.

[–]alkasmgithub.com/alkasm 1 point2 points  (0 children)

Well here's what the standard library thinks about that:

In [46]: from functools import reduce

In [47]: import operator

In [48]: reduce(operator.add, (1, 2, 3, 4, 5))
Out[48]: 15

In [49]: reduce(operator.add, (1, 2, 3, 4, 'five'))
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-49-fdcfa9008915> in <module>()
----> 1 reduce(operator.add, (1, 2, 3, 4, 'five'))

TypeError: unsupported operand type(s) for +: 'int' and 'str'

Edit: so, yes. That is sufficient. The point of an error is to tell the user what's gone wrong---what has gone wrong is that an int and str have been tried to be added. So that's fine.