Reputation: 1492
Is it possible to explicitly tell a function in python to use the default value of a parameter ?
For instance, if a function is defined as:
def foo(a=1, b=2, c=3):
pass
I would like to call the function like:
foo(a=3, b=<USE-DEFAULT>, c=10)
^
|
which should be equivalent to:
foo(a=3, c=10)
One usage example is if a function is used to instantiate an instance of a class:
class foo():
def __init__(a=1, b=2, c=3):
self.a = a
self.b = b
self.c = c
def create_foo(a=None, b=None, c=None):
f = foo( <PASS ALL EXCEPT NONE> )
F = create_foo(a=10, c=30)
# Then F should have a=10, b=2, c=30
In this example, I would like to avoid defining default values multiple times.
Upvotes: 2
Views: 1220
Reputation: 334
If you don't use *args and **kwargs and subclassing there is no reason to explicitly call the defaults and as long as you are using only your own classes and you don't need mutual default arguments, you can just hand over the same values as the defaults - BUT if you are working with *args and **kwargs and the method to be called is from a super class, you might get problems with the MRO. (See this article for further information: https://www.python.org/download/releases/2.3/mro/)
The only way I know to prevent a(n at this moment unknown) super class to pass an argument to the class your calss extends is to call the method explicidly and than hand over only the arguments you want it to get.
I don't see another use case for an explicit default call.
Upvotes: 2
Reputation: 6784
Just call that functions as
foo(a=3, c=10)
Alternatively, you could use the following approach, which is e.g. necessary for lists, because default values are evaluated in the module scope:
def foo(a=None, b=None, c=None):
local_a = a or "default"
...
foo(a=42, b=None, c=16)
None
then encodes to use the default, if None
is no valid option.
Finally, you could just defined the defaults as "constants":
DEFAULT_A = 42
DEFAULT_B = "foo"
DEFAULT_C = 17
def foo(a=DEFAULT_A, b=DEFAULT_B, c=DEFAULT_C):
pass
foo(16, DEFAULT_B, 123)
But this is quite uncommon.
For you updated example, I would propose to use *
and **
operators:
def create_foo(*args, **kwargs):
f = foo(*args, **kwargs)
create_foo(42, b="non-default")
See this question for explanations how these operators work.
Upvotes: 4
Reputation: 1947
When defining
function, you can set the default value, so when you call
the function you do not need to pass the default argument to the function.
def foo(a=1, b=<USE-DEFAULT>, c=3):
print(b)
foo(a=3, c=10)
In above function foo
, you are actually setting the default
value for all arguments a, b, c
example:
>>> def foo(a=1, b=2, c=3):
... print('a: {0}, b: {1}, c: {2}'.format(a, b, c))
...
>>> foo(a=3, c=10)
a: 3, b: 2, c: 10
>>> foo()
a: 1, b: 2, c: 3
>>> foo(a=3)
a: 3, b: 2, c: 3
>>> foo(a=3, c=10, b=5)
a: 3, b: 5, c: 10
>>>
Upvotes: 0