Conceptos avanzados sobre funciones
Tipos de argumentos: posicionales o keyword
Tenemos dos tipos de parámetros: los posiciónales donde el parámetro real debe coincidir en posición con el parámetro formal:
>>> def sumar(n1,n2):
... return n1+n2
...
>>> sumar(5,7)
12
>>> sumar(4)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: sumar() missing 1 required positional argument: 'n2'
Además podemos tener parámetros con valores por defecto:
>>> def operar(n1,n2,operador='+',respuesta='El resultado es '):
... if operador=="+":
... return respuesta+str(n1+n2)
... elif operador=="-":
... return respuesta+str(n1-n2)
... else:
... return "Error"
...
>>> operar(5,7)
'El resultado es 12'
>>> operar(5,7,"-")
'El resultado es -2'
>>> operar(5,7,"-","La resta es ")
'La resta es -2'
Los parámetros keyword son aquellos donde se indican el nombre del parámetro formal y su valor, por lo tanto no es necesario que tengan la misma posición. Al definir una función o al llamarla, hay que indicar primero los argumentos posicionales y a continuación los argumentos con valor por defecto (keyword).
>>> operar(5,7) # dos parámetros posicionales
>>> operar(n1=4,n2=6) # dos parámetros keyword
>>> operar(4,6,respuesta="La suma es") # dos parámetros posicionales y uno keyword
>>> operar(4,6,respuesta="La resta es",operador="-") # dos parámetros posicionales y dos keyword
Parámetro *
Un parámetro *
entre los parámetros formales de una función, nos obliga a indicar los parámetros reales posteriores como keyword:
>>> def sumar(n1,n2,*,op="+"):
... if op=="+":
... return n1+n2
... elif op=="-":
... return n1-n2
... else:
... return "error"
...
>>> sumar(2,3)
5
>>> sumar(2,3,"-")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: sumar() takes 2 positional arguments but 3 were given
>>> sumar(2,3,op="-")
-1
Argumentos arbitrarios (*args y **kwargs)
Para indicar un número indefinido de argumentos posicionales al definir una función, utilizamos el símbolo *
:
>>> def sumar(n,*args):
... resultado=n
... for i in args:
... resultado+=i
... return resultado
...
>>> sumar(2)
2
>>> sumar(2,3,4)
9
Para indicar un número indefinido de argumentos keyword al definir una función, utilizamos el símbolo **
:
>>> def saludar(nombre="pepe",**kwargs):
... cadena=nombre
... for valor in kwargs.values():
... cadena=cadena+" "+valor
... return "Hola "+cadena
...
>>> saludar()
'Hola pepe'
>>> saludar("juan")
'Hola juan'
>>> saludar(nombre="juan",nombre2="pepe")
'Hola juan pepe'
>>> saludar(nombre="juan",nombre2="pepe",nombre3="maria")
'Hola juan maria pepe'
Por lo tanto podríamos tener definiciones de funciones del tipo:
>>> def f()
>>> def f(a,b=1)
>>> def f(a,*args,b=1)
>>> def f(*args,b=1)
>>> def f(*args,b=1,*kwargs)
>>> def f(*args,*kwargs)
>>> def f(*args)
>>> def f(*kwargs)
Desempaquetar argumentos: pasar listas y diccionarios
En caso contrario es cuando tenemos que pasar parámetros que lo tenemos guardados en una lista o en un diccionario.
Para pasar listas utilizamos el símbolo *
:
>>> lista=[1,2,3]
>>> sumar(*lista)
6
>>> sumar(2,*lista)
8
>>> sumar(2,3,*lista)
11
Podemos tener parámetros keyword guardados en un diccionario, para enviar un diccionario utilizamos el símbolo **
:
>>> datos={"nombre":"jose","nombre2":"pepe","nombre3":"maria"}
>>> saludar(**datos)
'Hola jose maria pepe'
Devolver múltiples resultados
La instrucción return
puede devolver cualquier tipo de resultados, por lo tanto es fácil devolver múltiples datos guardados en una lista o en un diccionario. Veamos un ejemplo en que devolvemos los datos en una tupla:
>>> def operar(n1,n2):
... return (n1+n2,n1-n2,n1*n2)
>>> suma,resta,producto = operar(5,2)
>>> suma
7
>>> resta
3
>>> producto
10