Articulo de referencia

Parámetro (programación informática)

En programación informática , un parámetro , o argumento formal , es una variable que representa un argumento para una llamada a función . [ 1 ] [ 2 ] [ 3 ] [ 4 ] La firma de un...

En programación informática , un parámetro , o argumento formal , es una variable que representa un argumento para una llamada a función . [ 1 ] [ 2 ] [ 3 ] [ 4 ] La firma de una función define sus parámetros. Una llamada implica evaluar cada expresión de argumento de una llamada y asociar el resultado con el parámetro correspondiente.

Por ejemplo, considere la función de Python

def add ( x : int , y : int ) -> int : return x + y

Las variables xy yson parámetros, cada uno de tipo int. Para la llamada add(2, 3), las expresiones 2y 3son argumentos. Para la llamada add(a + 1, b + 2), los argumentos son a + 1y b+2.

El paso de parámetros viene definido por el lenguaje de programación. La estrategia de evaluación define la semántica de cómo se pueden declarar los parámetros y cómo se pasan los argumentos a una función. Generalmente, con el paso por valor , un parámetro actúa como una nueva variable local inicializada con el valor del argumento. Si el argumento es una variable, la función no puede modificar su estado porque el parámetro es una copia. Con el paso por referencia , que requiere que el argumento sea una variable, el parámetro es un alias del argumento.

Ejemplo

El siguiente código fuente en C define una función llamada con un parámetro llamado ; tanto la función como el parámetro son de tipo . Para la llamada , el argumento se pasa a la función como el valor double 10 y se asigna a la variable de parámetro , y la función devuelve 0.5.salesTaxpricedoublesalesTax(10.00)10.00price

doble impuesto sobre las ventas ( doble precio ) { devolver 0,05 * precio ; }

Parámetros y argumentos

Los términos parámetro y argumento pueden tener diferentes significados en distintos lenguajes de programación. A veces se usan indistintamente, y el contexto es lo que distingue su significado. El término parámetro (a veces llamado parámetro formal ) se usa a menudo para referirse a la variable tal como se encuentra en la declaración de la función , mientras que argumento (a veces llamado parámetro real ) se refiere a la entrada real proporcionada en una instrucción de llamada a la función. Por ejemplo, si se define una función como def f(x): ..., entonces xes el parámetro, y si se llama por , a = ...; f(a)entonces aes el argumento. Un parámetro es una variable (no ligada), mientras que el argumento puede ser un literal o una variable o una expresión más compleja que involucre literales y variables. En el caso de paso por valor, lo que se pasa a la función es el valor del argumento (por ejemplo, f(2)y a = 2; f(a)son llamadas equivalentes), mientras que en el paso por referencia, con una variable como argumento, lo que se pasa es una referencia a esa variable, aunque la sintaxis para la llamada a la función podría permanecer igual. [ 5 ] La especificación para paso por referencia o paso por valor se haría en la declaración y/o definición de la función.

Los parámetros aparecen en las definiciones de procedimientos; los argumentos aparecen en las llamadas a procedimientos. En la definición de la función, f(x) = x * xla variable xes un parámetro; en la llamada a la función, f(2)el valor 2 es el argumento de la función. En términos generales, un parámetro es un tipo y un argumento es una instancia.

Un parámetro es una propiedad intrínseca del procedimiento, incluida en su definición. Por ejemplo, en muchos lenguajes, un procedimiento para sumar dos números enteros y calcular la suma requeriría dos parámetros, uno para cada número. En general, un procedimiento puede definirse con cualquier número de parámetros, o sin ninguno. Si un procedimiento tiene parámetros, la parte de su definición que los especifica se denomina lista de parámetros .

Por el contrario, los argumentos son las expresiones [ 6 ] que se proporcionan al procedimiento cuando se llama, generalmente una expresión que coincide con uno de los parámetros. A diferencia de los parámetros, que forman una parte inmutable de la definición del procedimiento, los argumentos pueden variar de una llamada a otra. Cada vez que se llama a un procedimiento, la parte de la llamada al procedimiento que especifica los argumentos se denomina lista de argumentos .

Aunque los parámetros también se denominan comúnmente argumentos, a veces se considera que estos son los valores o referencias asignados a las variables de los parámetros cuando se llama a la función en tiempo de ejecución . Al hablar del código que llama a una función, cualquier valor o referencia que se le pase son los argumentos, y el lugar del código donde se proporcionan estos valores o referencias es la lista de parámetros . Al hablar del código dentro de la definición de la función, las variables en la lista de parámetros de la función son los parámetros, mientras que los valores de los parámetros en tiempo de ejecución son los argumentos.

Consideremos la siguiente función en Csum , , que tiene dos parámetros, ay b. Esta función suma los valores pasados ​​a los parámetros y devuelve el resultado a quien la llama.

int suma ( int a , int b ) { return a + b ; }

A continuación se muestra un ejemplo de llamada sum. Las variables xy yse inicializan y luego se pasan sumcomo argumentos. En tiempo de ejecución, los valores asignados a estas variables se pasan a sum. En sum, los parámetros ay bse evalúan, obteniendo los argumentos 40y 2, respectivamente. Los valores de los argumentos se suman y el resultado se devuelve a quien realizó la llamada, donde se asigna a la variable result.

int x = 40 ; int y = 2 ; int resultado = suma ( x , y );

Debido a la diferencia entre parámetros y argumentos, es posible proporcionar argumentos inapropiados a un procedimiento. La llamada puede proporcionar demasiados o muy pocos argumentos, uno o más de ellos pueden ser de un tipo incorrecto, o pueden proporcionarse en el orden incorrecto. Cualquiera de estas situaciones provoca una discrepancia entre las listas de parámetros y argumentos, y el procedimiento a menudo devolverá una respuesta no deseada o generará un error en tiempo de ejecución .

Convención alternativa en Eiffel

Dentro del método y lenguaje de desarrollo de software Eiffel , los términos argumento y parámetro tienen usos distintos establecidos por convención. El término argumento se usa exclusivamente en referencia a las entradas de una rutina, [ 7 ] y el término parámetro se usa exclusivamente en la parametrización de tipos para clases genéricas . [ 8 ]

Considere la siguiente definición de rutina:

suma ( a : ENTERO ; b : ENTERO ): ENTERO hacer Resultado := a + b fin

La rutina sumtoma dos argumentos ay b, que se denominan argumentos formales de la rutina . Una llamada a sumespecifica los argumentos reales , como se muestra a continuación con xy y.

resultado : ENTERO x : ENTERO = 40 y : ENTERO = 2 resultado := suma ( x , y )

Los parámetros también se consideran formales o reales . Los parámetros genéricos formales se utilizan en la definición de clases genéricas. En el siguiente ejemplo, la clase HASH_TABLE se declara como una clase genérica que tiene dos parámetros genéricos formales, Gque representan los datos de interés y Kla clave hash para dichos datos:

clase HASH_TABLE [ G , K -> HASHABLE ] 

Cuando una clase se convierte en cliente de HASH_TABLE, los parámetros genéricos formales se sustituyen por parámetros genéricos reales en una derivación genérica . En la siguiente declaración de atributo, my_dictionaryse utilizará como un diccionario basado en cadenas de caracteres . Por lo tanto, tanto los parámetros genéricos formales de datos como de clave se sustituyen por parámetros genéricos reales de tipo .STRING

mi_diccionario : HASH_TABLE [ CADENA , CADENA ]

Tipos de datos

En los lenguajes de programación fuertemente tipados , el tipo de cada parámetro debe especificarse en la declaración del procedimiento. Los lenguajes que utilizan inferencia de tipos intentan descubrir los tipos automáticamente a partir del cuerpo y el uso de la función. Los lenguajes de programación de tipado dinámico posponen la resolución de tipos hasta el tiempo de ejecución. Los lenguajes de tipado débil realizan poca o ninguna resolución de tipos, confiando en cambio en el programador para la corrección.

Algunos lenguajes utilizan una palabra clave especial (por ejemplo, void) para indicar que la función no tiene parámetros; en la teoría formal de tipos , dichas funciones toman una lista de parámetros vacía (cuyo tipo no es void, sino unit ).

Pase de argumento

El mecanismo para asignar argumentos a los parámetros, denominado paso de argumentos , depende de la estrategia de evaluación utilizada para ese parámetro (normalmente paso por valor ), que puede especificarse mediante palabras clave.

argumentos predeterminados

Algunos lenguajes de programación como Ada , C++ , Clojure , Common Lisp , [ 9 ] Fortran 90 , [ 10 ] Python , Ruby , Tcl y Windows PowerShell permiten que un argumento predeterminado se proporcione explícita o implícitamente en la declaración de una función. Esto permite que quien llama a la función omita ese argumento al llamarla. Si el argumento predeterminado se proporciona explícitamente, entonces ese valor se usa si quien llama a la función no lo proporciona. Si el argumento predeterminado es implícito (a veces usando una palabra clave como Optional ), entonces el lenguaje proporciona un valor conocido (como null , Empty , zero, una cadena vacía, etc.) si quien llama a la función no proporciona un valor.

Ejemplo de PowerShell:

function doc ( $g = 1 . 21 ) { "$g gigavatios? $g gigavatios? ¡Santo cielo!" }
PD > ¿ Documento 1,21 gigavatios? ¿1,21 gigavatios? ¡Santo cielo!PD > ¿ Documento 88 ? ¿88 gigavatios? ¡Santo cielo!

Los argumentos predeterminados pueden considerarse un caso especial de la lista de argumentos de longitud variable.

Listas de parámetros de longitud variable

Algunos lenguajes permiten definir funciones que aceptan un número variable de argumentos . En estos lenguajes, las funciones deben iterar a través de la lista de argumentos.

Ejemplo de PowerShell:

función marty { $args | para cada { "volver al año $_" } }
PD > Marty 1985 regresa al año 1985PD > marty 2015 1985 1955 volver al año 2015 volver al año 1985 volver al año 1955

Parámetros con nombre

Algunos lenguajes de programación, como Ada y Windows PowerShell , permiten que las funciones tengan parámetros con nombre . Esto facilita la autoexplicación del código que realiza la llamada . Además, ofrece mayor flexibilidad a quien llama a la función, permitiendo a menudo cambiar el orden de los argumentos o incluso omitirlos según sea necesario.

Ejemplo de PowerShell:

función jennifer ( $adjectiveYoung , $adjectiveOld ) { "Jennifer joven: ¡Soy $adjectiveYoung!" "Jennifer mayor: ¡Soy $adjectiveOld!" }
PS > Jennifer 'fresca' 'experimentada' Jennifer joven: ¡Soy fresca! Jennifer mayor: ¡Soy experimentada!PS > Jennifer -adjetivoVieja 'experimentada' -adjetivoJoven 'fresca' Joven Jennifer: ¡Soy fresca! Vieja Jennifer: ¡Soy experimentada!

Múltiples parámetros en lenguajes funcionales

En el cálculo lambda , cada función tiene exactamente un parámetro. Lo que se considera una función con múltiples parámetros se representa en el cálculo lambda como una función que toma el primer argumento y devuelve una función que toma el resto de los argumentos. Esta transformación se denomina currificación . Algunos lenguajes de programación, como ML y Haskell , siguen este esquema. En estos lenguajes, cada función tiene exactamente un parámetro, y lo que puede parecer la definición de una función con múltiples parámetros es, en realidad, azúcar sintáctico para la definición de una función que devuelve otra función, etc. La aplicación de funciones es asociativa por la izquierda en estos lenguajes y en el cálculo lambda, por lo que lo que parece una aplicación de una función a múltiples argumentos se evalúa correctamente como la función aplicada al primer argumento, luego la función resultante aplicada al segundo argumento, etc.

Parámetros de salida

Un parámetro de salida , también conocido como parámetro de salida o parámetro de retorno , es un parámetro utilizado para la salida, en lugar del uso más habitual para la entrada. El uso de parámetros por referencia , o parámetros por valor donde el valor es una referencia, como parámetros de salida es un modismo en algunos lenguajes, especialmente C y C++, [ a ] mientras que otros lenguajes tienen soporte integrado para parámetros de salida. Los lenguajes con soporte integrado para parámetros de salida incluyen Ada [ 11 ] (ver subprogramas de Ada ), Fortran (desde Fortran 90 ; ver "intent" de Fortran ), varias extensiones procedimentales de SQL , como PL/SQL (ver funciones de PL/SQL ) [ 12 ] y Transact-SQL , C# [ 13 ] y .NET Framework , [ 14 ] Swift , [ 15 ] y el lenguaje de scripting TScript (ver declaraciones de funciones de TScript ).

Aquí tienes un ejemplo de un "parámetro de salida" en C++:

// Definición de una función con un parámetro de salida void sum ( int x , int y , int & out ) { out = x + y ; }// Uso: int foo = 1 ; int bar = 2 ; int baz ; sum ( foo , bar , baz );

La función no devolverá nada, pero el valor x + yse asignará a la variable a la que se pasa una referenciaout como .

Más precisamente, se pueden distinguir tres tipos de parámetros o modos de parámetros :parámetros de entrada s,parámetros de salidayParámetros de entrada/salida ;estos se suelen denotar comoin,out, yin outoinout. Un argumento de entrada (el argumento de un parámetro de entrada) debe ser un valor, como una variable inicializada o un literal, y no debe ser redefinido ni asignado. Un argumento de salida debe ser una variable asignable, pero no necesita estar inicializada, cualquier valor existente no es accesible y debe tener un valor asignado. Un argumento de entrada/salida debe ser una variable inicializada y asignable, y opcionalmente puede tener un valor asignado. Los requisitos exactos y su aplicación varían entre lenguajes; por ejemplo, enAda 83los parámetros de salida solo pueden ser asignados, no leídos, incluso después de la asignación (esto se eliminó enAda 95para eliminar la necesidad de una variable acumuladora auxiliar). Estos son análogos a la noción de unvaloren una expresión como un rvalue (tiene un valor), un lvalue (puede ser asignado) o un rvalue/lvalue (tiene un valor y puede ser asignado), respectivamente, aunque estos términos tienen significados especializados en C y C++.

En algunos casos, solo se distingue entre entrada y entrada/salida, considerando la salida un uso específico de entrada/salida; en otros casos, solo se admite entrada y salida (pero no entrada/salida). El modo predeterminado varía según el lenguaje: en Fortran 90, la entrada/salida es la predeterminada, mientras que en C# y las extensiones SQL, la entrada es la predeterminada, y en TScript, cada parámetro se especifica explícitamente como entrada o salida.

Sintácticamente, el modo de parámetros se indica generalmente con una palabra clave en la declaración de la función, como en C#. Por convención, los parámetros de salida suelen colocarse al final de la lista de parámetros para distinguirlos claramente, aunque esto no siempre se sigue. TScript utiliza un enfoque diferente, donde en la declaración de la función se enumeran primero los parámetros de entrada y luego los de salida, separados por dos puntos (:), y no hay un tipo de retorno para la función en sí, como en esta función, que calcula el tamaño de un fragmento de texto:voidFn(outintx)

TextExtent ( WString texto , Fuente fuente : Ancho entero , Alto entero )

Los modos de parámetros son una forma de semántica denotacional , que indica la intención del programador y permite a los compiladores detectar errores y aplicar optimizaciones; no implican necesariamente una semántica operacional (cómo se produce realmente el paso de parámetros). Cabe destacar que, si bien los parámetros de entrada pueden implementarse por valor, y los parámetros de salida y de entrada/salida por referencia (y esta es una forma sencilla de implementar estos modos en lenguajes sin soporte integrado), no siempre se implementan de esta manera. Esta distinción se analiza en detalle en la Rationale de Ada '83, que enfatiza que el modo de parámetro se abstrae del mecanismo de paso de parámetros (por referencia o por copia) que se implementa realmente. [ 11 ] Por ejemplo, mientras que en C# los parámetros de entrada (por defecto, sin palabra clave) se pasan por valor, y los parámetros de salida y de entrada/salida ( outy ref) se pasan por referencia, en PL/SQL los parámetros de entrada ( IN) se pasan por referencia, y los parámetros de salida y de entrada/salida ( OUTy IN OUT) se pasan por valor por defecto y el resultado se copia de vuelta, pero pueden pasarse por referencia utilizando la sugerencia NOCOPYdel compilador . [ 16 ]

Una construcción sintácticamente similar a la de los parámetros de salida consiste en asignar el valor de retorno a una variable con el mismo nombre que la función. Esto se encuentra en Pascal y Fortran 66 y Fortran 77 , como en este ejemplo de Pascal:

función f ( x , y : entero ) : entero ; inicio f := x + y ; fin ;

Esto es semánticamente diferente, ya que cuando se llama a la función, simplemente se evalúa; no se le pasa una variable desde el ámbito de la llamada para almacenar el resultado.

Usar

El uso principal de los parámetros de salida es devolver múltiples valores desde una función, mientras que el uso de los parámetros de entrada/salida es modificar el estado mediante el paso de parámetros (en lugar de mediante un entorno compartido, como en las variables globales). Un uso importante de devolver múltiples valores es resolver el problema del semipredicado de devolver tanto un valor como un estado de error; véase Problema del semipredicado: retorno multivalor .

Por ejemplo, para devolver dos variables desde una función en C, se puede escribir:

ancho entero ; alto entero ;f ( x , & ancho , & alto );

donde xes un parámetro de entrada y widthy heightson parámetros de salida; el signo & en &widthy &heightdenota las direcciones de memoria de widthy height.

Un caso de uso común en C y lenguajes relacionados es el manejo de excepciones , donde una función coloca el valor de retorno en una variable de salida y devuelve un valor booleano que indica si la función tuvo éxito o no. Un ejemplo arquetípico es el TryParsemétodo en .NET, especialmente en C#, que analiza una cadena y la convierte en un entero, devolviendo trueverdadero o falsefalso en caso de éxito. Su firma es la siguiente: [ 17 ]

public static bool TryParse ( string s , out int result )

y puede utilizarse de la siguiente manera:

usando el sistema ;int resultado ; si ( ! Int32.TryParse ( s , resultado )) { // manejo de excepciones }

Consideraciones similares se aplican a la devolución de un valor de uno de varios tipos posibles, donde el valor devuelto puede especificar el tipo y luego el valor se almacena en una de varias variables de salida.

Desventajas

En la programación moderna, a menudo se desaconseja el uso de parámetros de salida, principalmente por ser engorrosos, confusos y de bajo nivel; los valores de retorno comunes son considerablemente más fáciles de entender y manejar. [ 18 ] Cabe destacar que los parámetros de salida implican funciones con efectos secundarios (que modifican el parámetro de salida) y son semánticamente similares a las referencias, que son más confusas que las funciones y los valores puros, y la distinción entre parámetros de salida y parámetros de entrada/salida puede ser sutil. Además, dado que en los estilos de programación comunes la mayoría de los parámetros son simplemente parámetros de entrada, los parámetros de salida y los parámetros de entrada/salida son inusuales y, por lo tanto, susceptibles de malentendidos.

Los parámetros de salida y de entrada/salida impiden la composición de funciones , ya que la salida se almacena en variables, en lugar de en el valor de una expresión. Por lo tanto, primero se debe declarar una variable y luego cada paso de una cadena de funciones debe ser una instrucción independiente. Por ejemplo, en C++ la siguiente composición de funciones:

MyObject obj = g ( y , f ( x ));

cuando se escribe con parámetros de salida y entrada/salida se convierte en (ya que Fes un parámetro de salida, para Gun parámetro de entrada/salida):

MiObjeto obj ; f ( x , & obj ); g ( y , & obj );

En el caso especial de una función con un único parámetro de salida o de entrada/salida y sin valor de retorno, la composición de funciones es posible si el parámetro de salida o de entrada/salida (o en C/C++, su dirección) también es devuelto por la función, en cuyo caso lo anterior se convierte en:

MiObjeto obj ; g ( y , f ( x , & obj ));

Alternativas

Existen diversas alternativas para los casos de uso de los parámetros de salida.

Para devolver múltiples valores desde una función, una alternativa es devolver una tupla . Sintácticamente, esto es más claro si se puede utilizar el desempaquetado automático de secuencias y la asignación paralela , como en Go o Python, por ejemplo:

def f () -> tupla [ int , int ]: return 1 , 2 a , b = f ()

Para devolver un valor de uno de varios tipos, se puede usar una unión etiquetada ; los casos más comunes son los tipos anulables ( tipos de opción ), donde el valor de retorno puede ser nulo para indicar un fallo. Para el manejo de excepciones, se puede devolver un tipo anulable o generar una excepción. Por ejemplo, en Python se podría tener:

resultado : str = parse ( s ) si resultado es None : # manejo de excepciones

o, de forma más idiomática:

try : result : str = parse ( s ) except ParseError : # manejo de excepciones

La microoptimización de no requerir una variable local y copiar el valor de retorno al usar variables de salida también puede aplicarse a funciones convencionales y valores de retorno mediante compiladores suficientemente sofisticados.

La alternativa habitual a los parámetros de salida en C y lenguajes relacionados es devolver una única estructura de datos que contenga todos los valores de retorno. [ 13 ] Por ejemplo, dada una estructura que encapsula el ancho y la altura, se puede escribir:

AnchoAlto wh = f ( x );

En los lenguajes orientados a objetos, en lugar de usar parámetros de entrada/salida, a menudo se puede usar la llamada por compartición , pasando una referencia a un objeto y luego modificando el objeto, aunque sin cambiar a qué objeto se refiere la variable. [ 18 ]

Véase también

Notas

  1. C y C++ utilizan paso por valor, pero si el tipo es una referencia (un puntero C/C++ o una referencia C++), entonces se puede utilizar el establecimiento del valor de la referencia para producir un comportamiento de estilo de paso por referencia.

Referencias

  1. "Pasar información a un método o un constructor (Aprendiendo el lenguaje Java > Clases y objetos)" . Los tutoriales de Java™ . Consultado el 9 de septiembre de 2021. Los parámetros se refieren a la lista de variables en la declaración de un método. Los argumentos son los valores reales que se pasan cuando se invoca el método. Al invocar un método, los argumentos utilizados deben coincidir con los parámetros de la declaración en tipo y orden.
  2. ^ Prata, Stephen (2004). C primer plus (5ª ed.). Sam. págs. 276–277 . ISBN   978-0-672-32696-7.
  3. "Borrador de trabajo, estándar para el lenguaje de programación C++" (PDF) . Estándares abiertos . 19 de octubre de 2005. Archivado del original (PDF) el 14 de diciembre de 2005. Consultado el 1 de enero de 2018 .
  4. Gordon, Aaron. "Subprogramas y paso de parámetros" . rowdysites.msudenver.edu/~gordona . Archivado del original el 1 de enero de 2018. Consultado el 1 de enero de 2018 .
  5. Dollard, Kathleen. "Paso de argumentos por valor y por referencia (Visual Basic)" . Microsoft Learn . Consultado el 27 de octubre de 2018 .
  6. "El tutorial de programación en C de GNU" . crasseux.com . Consultado el 27 de octubre de 2018 .
  7. Meyer, Bertrand. Construcción de software orientado a objetos , 2.ª edición, Prentice Hall, 1997, pág. 444.
  8. Meyer, pág. 96.
  9. "Funciones" . gigamonkeys.com . Consultado el 2 de junio de 2021 .
  10. "argumentos opcionales" . www.netlib.org . Consultado el 2 de junio de 2021 .
  11. 1 2 8.2 Modos de parámetros , " Fundamentos del diseño del lenguaje de programación Ada® "
  12. 8. Subprogramas PL/SQL: Especificación de los modos de parámetros de los subprogramas
  13. 1 2 Peter Hallam. "¿Por qué C# tiene tanto 'ref' como 'out'?" . Archivado del original el 26-09-2011.
  14. Enumeración de dirección de parámetros
  15. Funciones — El lenguaje de programación Swift (Swift 4.2)
  16. 8. Subprogramas PL/SQL: Paso de grandes estructuras de datos con la sugerencia del compilador NOCOPY
  17. Método Int32.TryParse (String, Int32)
  18. 1 2 CA1021: Evitar parámetros de salida