En C#, las tuplas son estructuras de datos ligeras que permiten agrupar múltiples valores de diferentes tipos en una sola unidad.
A diferencia de las clases o structs, las tuplas son más sencillas y están diseñadas para simplificar el manejo de múltiples valores (nos evitan tener que definir tipos adicionales).
En C# las tuplas son inmutables. Eso significa que una vez creadas, sus valores no pueden ser cambiados.
Si quieres aprender más sobre Tuplas
consulta el Curso de Introducción a la Programación leer más
Sintaxis de las tuplas
Las tuplas se pueden declarar utilizando el operador ()
de la siguiente forma.
var tupla = (valor1, valor2);
Donde,
- valor1, valor2 son los valores que integran la tupla.
Es posible crear una tupla con cualquier número de valores. En el ejemplo anterior he puesto dos, pero podrían ser tres, cuatro, o los que queráis.
var tupla = (valor1, valor2, valor3, ...);
Aunque tampoco conviene crear una tupla larguísima, no es su propósito.
Ejemplo básico
Lo vemos más fácil con un ejemplo. Así crearíamos una tupla en C#,
var miTupla = (1, "Hola", 3.14);
En este caso hemos creado una tupla con contiene un int
, un string
y un double
.
También podríamos declarar la tupla explícitamente, con la que especificamos los tipos de la tupla.
(int, string, double) miTupla = (1, "Hola", 3.14);
Finalmente, podemos crear la tupla a partir de la clase Tuple<...>
.
Tuple<int, string, bool> tupla = new Tuple<int, string, bool>(1, "Hola", true);
Pero francamente, no entiendo porque alguien querría hacer esto, teniendo la sintaxis anterior 😆.
Uso básico
Acceso a los elementos de la tupla
Podemos acceder a los elementos de una tupla se acceden utilizando las propiedades Item1
, Item2
, etc.
var tupla = (1, "Hola", true);
Console.WriteLine(tupla.Item1); // 1
Console.WriteLine(tupla.Item2); // Hola
Console.WriteLine(tupla.Item3); // True
Tuplas con nombre
También es posible asignar nombres a los elementos de una tupla. Esto se conoce como tuplas nombradas. En general, son más cómodas que las tuplas “sin nombre”.
var tupla = (numero: 1, texto: "Hola", booleano: true);
Console.WriteLine(tupla.numero); // 1
Console.WriteLine(tupla.texto); // Hola
Console.WriteLine(tupla.booleano); // True
Destructuración de tuplas
También podemos utilizar la sintaxis de desestructuración en tuplas, para descomponerla en sus valores originales.
var tupla = (1, "Hola", 3.14);
var (entero, cadena, numero) = tupla;
// si prefieres especificar los tipos
(int numero, string texto, bool booleano) = tupla;
En este caso, estamos asignando los elementos de la tupla tupla
a variables individuales utilizando la sintaxis de desestructuración con los nombres asignados.
Ejemplos prácticos
Método que retorna una tupla
Uno de los usos más comunes de las tuplas es en los métodos que necesitan retornar múltiples valores:
// Método que calcula la suma y el producto de dos números
public static (int suma, int producto) Calcular(int a, int b)
{
int suma = a + b; // Calcular la suma
int producto = a * b; // Calcular el producto
return (suma, producto); // Retornar una tupla con los resultados
}
// Uso
var resultado = Calcular(3, 4); // Llamar al método y almacenar el resultado en una tupla
Console.WriteLine($"Suma: {resultado.suma}, Producto: {resultado.producto}"); // Imprimir los resultados
En este ejemplo, el método Calcular
retorna una tupla que contiene la suma y el producto de dos números enteros.
Tuplas como parámetros de métodos
Las tuplas también se pueden usar como parámetros en los métodos, permitiendo pasar múltiples valores en una única unidad:
// Método que muestra información de una persona usando una tupla como parámetro
public static void MostrarInformacion((string nombre, int edad) persona)
{
Console.WriteLine($"Nombre: {persona.nombre}, Edad: {persona.edad}"); // Imprimir el nombre y la edad
}
// Uso
var persona = (nombre: "Luis", edad: 30); // Crear una tupla con el nombre y la edad
MostrarInformacion(persona); // Llamar al método con la tupla como argumento
Comparación de tuplas
Las tuplas en C# pueden compararse directamente usando operadores de comparación:
// Crear tuplas para comparar
var tupla1 = (1, "Hola");
var tupla2 = (1, "Hola");
var tupla3 = (2, "Adiós");
// Comparar tuplas
bool sonIguales = tupla1 == tupla2; // true
bool sonDiferentes = tupla1 != tupla3; // true
// Imprimir resultados de la comparación
Console.WriteLine($"tupla1 == tupla2: {sonIguales}");
Console.WriteLine($"tupla1 != tupla3: {sonDiferentes}");
Uso de tuplas en LINQ
Las tuplas son muy útiles en las consultas LINQ, especialmente cuando se necesita devolver múltiples valores:
// Crear una lista de tuplas que representan personas
var personas = new List<(string nombre, int edad)>
{
("Luis", 25),
("María", 30),
("Pedro", 28)
};
// Filtrar y seleccionar personas mayores de 25 años usando LINQ
var mayoresDe25 = personas
.Where(p => p.edad > 25)
.Select(p => (p.nombre, p.edad));
// Imprimir las personas filtradas
foreach (var persona in mayoresDe25)
{
Console.WriteLine($"Nombre: {persona.nombre}, Edad: {persona.edad}");
}
Uso de tuplas como clave de un diccionario
Otro uso interesantes es emplear tuplas como claves múltiples en un diccionario. Esto es posible dado que las tuplas son inmutables.
Esto es muy útil para buscar rápidamente valores basados en múltiples criterios.
// Crear un diccionario con tuplas como claves y strings como valores
var empleados = new Dictionary<(string departamento, int id), string>();
// Añadir elementos al diccionario
empleados.Add(("Ventas", 101), "Luis Pérez");
empleados.Add(("Marketing", 102), "María López");
empleados.Add(("TI", 103), "Pedro González");
// Buscar empleados en el diccionario usando tuplas como claves
var empleadoVentas = empleados[("Ventas", 101)];
var empleadoMarketing = empleados[("Marketing", 102)];
// Imprimir los resultados de la búsqueda
Console.WriteLine($"Empleado en Ventas con ID 101: {empleadoVentas}");
Console.WriteLine($"Empleado en Marketing con ID 102: {empleadoMarketing}");