Skip to content

Capítulo 4: Funciones ​

4.1 Nivel Introductorio ​

Definición y declaración de funciones ​

Una función es un bloque de código reutilizable que realiza una tarea específica. Las funciones ayudan a modularizar el código, facilitando su mantenimiento y comprensión.

Sintaxis básica de una función:

cpp
tipo_de_retorno nombre_función(parámetros) {
    // Cuerpo de la función
    // Instrucciones a ejecutar
}
  • tipo_de_retorno: Es el tipo de dato que la función devolverá al ser llamada. Si no devuelve nada, se utiliza void.
  • nombre_función: Identificador único de la función.
  • parámetros: Variables que recibe la función como entrada.

Ejemplo de una función simple:

cpp
int sumar(int a, int b) {
    int resultado = a + b;
    return resultado;
}

Parámetros y argumentos ​

Parámetros ​

Los parámetros son variables definidas en la declaración de la función que reciben los valores proporcionados al llamar a la función.

Ejemplo:

En la función sumar, int a y int b son parámetros.

Argumentos ​

Los argumentos son los valores reales que se pasan a la función cuando se llama.

Ejemplo de llamada a función:

cpp
int resultado = sumar(5, 3);

Aquí, 5 y 3 son los argumentos que se pasan a los parámetros a y b.

Valor de retorno ​

Una función puede devolver un valor al código que la llamó utilizando la palabra clave return.

Ejemplo:

cpp
double multiplicar(double x, double y) {
    return x * y;
}

Si la función no necesita devolver un valor, se declara con void y puede omitir el return.

Ejemplo de función void:

cpp
void saludar() {
    std::cout << "¡Hola!" << std::endl;
}

Llamada a la función:

cpp
saludar(); // Imprime "¡Hola!"

4.2 Nivel Intermedio ​

Sobrecarga de funciones ​

La sobrecarga permite crear múltiples funciones con el mismo nombre pero con diferentes parámetros. El compilador determina cuál función llamar en función de los argumentos proporcionados.

Ejemplo:

cpp
int sumar(int a, int b) {
    return a + b;
}

double sumar(double a, double b) {
    return a + b;
}

int sumar(int a, int b, int c) {
    return a + b + c;
}

Uso:

cpp
int resultado1 = sumar(2, 3);          // Llama a sumar(int, int)
double resultado2 = sumar(2.5, 3.5);   // Llama a sumar(double, double)
int resultado3 = sumar(1, 2, 3);       // Llama a sumar(int, int, int)

Funciones inline ​

Las funciones inline sugieren al compilador que inserte el código de la función en el lugar donde es llamada, en lugar de realizar una llamada normal a función. Esto puede mejorar el rendimiento en funciones pequeñas y llamadas frecuentes.

Sintaxis:

cpp
inline int cuadrado(int x) {
    return x * x;
}

Uso:

cpp
int valor = cuadrado(5); // valor = 25

Nota: El compilador puede ignorar la sugerencia inline si lo considera apropiado.

Parámetros por defecto ​

Los parámetros por defecto permiten asignar un valor predeterminado a los parámetros de una función. Si no se proporciona un argumento al llamar a la función, se utiliza el valor por defecto.

Sintaxis:

cpp
void mostrarMensaje(std::string mensaje = "Hola, Mundo") {
    std::cout << mensaje << std::endl;
}

Uso:

cpp
mostrarMensaje();                      // Imprime "Hola, Mundo"
mostrarMensaje("Bienvenido a C++");    // Imprime "Bienvenido a C++"

Reglas:

  • Los parámetros con valores por defecto deben estar al final de la lista de parámetros.
  • Si una función tiene múltiples parámetros con valores por defecto, y se omiten algunos argumentos, se asignan en orden desde el final.

4.3 Nivel Avanzado ​

Plantillas de funciones (templates) ​

Las plantillas de funciones permiten escribir funciones genéricas que pueden trabajar con diferentes tipos de datos sin duplicar el código.

Sintaxis básica:

cpp
template <typename T>
T maximo(T a, T b) {
    return (a > b) ? a : b;
}

Uso:

cpp
int maxEntero = maximo(5, 10);            // Trabaja con int
double maxDouble = maximo(3.14, 2.71);    // Trabaja con double
char maxChar = maximo('a', 'z');          // Trabaja con char

Explicación:

  • template <typename T>: Declara una plantilla con un parámetro de tipo T.
  • Dentro de la función, T se utiliza como si fuera un tipo normal.
  • Al llamar a la función, el compilador deduce el tipo T en función de los argumentos.

Funciones recursivas ​

Una función recursiva es aquella que se llama a sí misma. Es útil para resolver problemas que pueden dividirse en subproblemas similares.

Ejemplo: Factorial de un número

cpp
int factorial(int n) {
    if (n <= 1) {
        return 1; // Caso base
    } else {
        return n * factorial(n - 1); // Llamada recursiva
    }
}

Uso:

cpp
int resultado = factorial(5); // resultado = 120

Consideraciones:

  • Es importante definir un caso base para evitar recursiones infinitas.
  • Las funciones recursivas pueden consumir más memoria debido a las llamadas acumuladas en la pila de ejecución.

Expresiones lambda y funciones anónimas ​

Las expresiones lambda son funciones anónimas que se pueden definir en línea. Introducidas en C++11, son útiles para definir funciones pequeñas sin necesidad de declararlas por separado.

Sintaxis básica:

cpp
[captura](parámetros) -> tipo_retorno {
    // Cuerpo de la función
};
  • [captura]: Especifica qué variables externas a la lambda se pueden usar dentro de ella.
  • (parámetros): Lista de parámetros de la función.
  • -> tipo_retorno: (Opcional) Especifica el tipo de retorno.
  • Cuerpo: Código que se ejecuta cuando se llama a la lambda.

Ejemplo:

cpp
auto sumar = [](int a, int b) -> int {
    return a + b;
};

int resultado = sumar(3, 4); // resultado = 7

Captura de variables ​

  • Por valor [=]: Captura todas las variables externas por valor (copia).
  • Por referencia [&]: Captura todas las variables externas por referencia.
  • Captura específica: Se pueden capturar variables individuales por valor o referencia.

Ejemplo de captura:

cpp
int factor = 2;

auto multiplicar = [factor](int x) {
    return x * factor;
};

int resultado = multiplicar(5); // resultado = 10

Uso con algoritmos de la STL ​

Las lambdas son especialmente útiles con los algoritmos de la Biblioteca Estándar.

Ejemplo:

cpp
std::vector<int> numeros = {1, 2, 3, 4, 5};

std::for_each(numeros.begin(), numeros.end(), [](int n) {
    std::cout << n << " ";
});

// Salida: 1 2 3 4 5

Ejemplo con std::sort:

cpp
std::vector<int> valores = {5, 2, 8, 3, 1};

std::sort(valores.begin(), valores.end(), [](int a, int b) {
    return a > b; // Orden descendente
});

// valores = {8, 5, 3, 2, 1}