Uso de tipos de registro

Tip

¿No está familiarizado con el desarrollo de software? Comience primero con los tutoriales de introducción . Te familiarizas con las clases, los métodos y los bucles allí.

¿Competente en otro idioma? Este tutorial se centra en las características de registro de C# que se usan todos los días: igualdad de valores, sintaxis posicional y with expresiones.

En este tutorial, creará una aplicación de consola que modela las temperaturas diarias mediante registros y estructuras de registros.

En este tutorial aprenderá a:

  • Declarar registros posicionales y estructuras de registro.
  • Cree una jerarquía de registros pequeña.
  • Utilice la igualdad y el formato generados por el compilador.
  • Utiliza with expresiones para la mutación no destructiva.

Prerrequisitos

Instrucciones de instalación

En Windows, este archivo de configuración WinGet se utiliza para instalar todos los requisitos previos. Si ya tiene algo instalado, WinGet omitirá ese paso.

  1. Descargue el archivo y haga doble clic para ejecutarlo.
  2. Lea el contrato de licencia, escriba yy seleccione Escriba cuando se le pida que acepte.
  3. Si recibe un mensaje de control de cuentas de usuario (UAC) parpadeante en la barra de tareas, permita que la instalación continúe.

En otras plataformas, debe instalar cada uno de estos componentes por separado.

  1. Descargue el instalador recomendado en la página de descarga del SDK .NET y haga doble clic para ejecutarlo. La página de descarga detecta la plataforma y recomienda el instalador más reciente para la plataforma.
  2. Descargue el instalador más reciente de la página principal Visual Studio Code y haga doble clic para ejecutarlo. Esa página también detecta tu plataforma y el vínculo debe ser correcto para tu sistema operativo.
  3. Haga clic en el botón "Instalar" de la página de extensión C# DevKit. Esto abre Visual Studio código y le pregunta si desea instalar o habilitar la extensión. Seleccione "instalar".

Creación de la aplicación y el primer registro

Cree una carpeta para la aplicación, ejecute dotnet new consoley abra el proyecto generado.

Agregue un archivo denominado DailyTemperature.csy agregue un valor posicional readonly record struct para los valores de temperatura:

public readonly record struct DailyTemperature(double HighTemp, double LowTemp)
{
    public double Mean => (HighTemp + LowTemp) / 2.0;
}

Agregue un archivo denominado Program.csy cree datos de temperatura de ejemplo:

private static DailyTemperature[] data = [
    new DailyTemperature(HighTemp: 57, LowTemp: 30), 
    new DailyTemperature(60, 35),
    new DailyTemperature(63, 33),
    new DailyTemperature(68, 29),
    new DailyTemperature(72, 47),
    new DailyTemperature(75, 55),
    new DailyTemperature(77, 55),
    new DailyTemperature(72, 58),
    new DailyTemperature(70, 47),
    new DailyTemperature(77, 59),
    new DailyTemperature(85, 65),
    new DailyTemperature(87, 65),
    new DailyTemperature(85, 72),
    new DailyTemperature(83, 68),
    new DailyTemperature(77, 65),
    new DailyTemperature(72, 58),
    new DailyTemperature(77, 55),
    new DailyTemperature(76, 53),
    new DailyTemperature(80, 60),
    new DailyTemperature(85, 66) 
];

Esta sintaxis proporciona modelado de datos conciso con semántica de valores inmutables.

Agregar comportamiento a la estructura de registro

En DailyTemperature.cs, la estructura de registro ya tiene una propiedad calculada Mean :

public double Mean => (HighTemp + LowTemp) / 2.0;

Una estructura de registros funciona bien aquí porque cada valor es pequeño y independiente.

Crear tipos de registro para cálculos de grados-día

Note

Los grados de calefacción y los días de enfriamiento miden cuánto se desvía la temperatura media diaria de una temperatura base (normalmente 65°F/18°C). Los grados-día de calefacción se acumulan en días fríos cuando el promedio está por debajo de la base, mientras que los grados-día de refrigeración se acumulan en días cálidos cuando el promedio está por encima de la base. Estos cálculos ayudan a calcular el consumo energético de los edificios de calefacción o refrigeración, por lo que son útiles para empresas de servicios públicos, administradores de edificios y análisis climáticos.

Cree un archivo denominado DegreeDays.cs con una jerarquía para cálculos de grados-día de calefacción y refrigeración:

public abstract record DegreeDays(double BaseTemperature, IEnumerable<DailyTemperature> TempRecords);

public sealed record HeatingDegreeDays(double BaseTemperature, IEnumerable<DailyTemperature> TempRecords)
    : DegreeDays(BaseTemperature, TempRecords)
{
    public double DegreeDays => TempRecords.Where(s => s.Mean < BaseTemperature).Sum(s => BaseTemperature - s.Mean);
}

public sealed record CoolingDegreeDays(double BaseTemperature, IEnumerable<DailyTemperature> TempRecords)
    : DegreeDays(BaseTemperature, TempRecords)
{
    public double DegreeDays => TempRecords.Where(s => s.Mean > BaseTemperature).Sum(s => s.Mean - BaseTemperature);
}

Ahora calcula los totales a partir del método Main en Program.cs:

var heatingDegreeDays = new HeatingDegreeDays(65, data);
Console.WriteLine(heatingDegreeDays);

var coolingDegreeDays = new CoolingDegreeDays(65, data);
Console.WriteLine(coolingDegreeDays);

La salida generada de ToString es útil para diagnósticos rápidos mientras itera.

Anular PrintMembers para personalizar la salida

Cuando la salida predeterminada incluye demasiado ruido, invalide PrintMembers en el registro base:

protected virtual bool PrintMembers(StringBuilder stringBuilder)
{
    stringBuilder.Append($"BaseTemperature = {BaseTemperature}");
    return true;
}

La invalidación mantiene la salida centrada en la información que necesita.

Uso de expresiones para la mutación no destructiva

Use with para crear copias modificadas sin mutar el registro original:

// Growing degree days measure warming to determine plant growing rates
var growingDegreeDays = coolingDegreeDays with { BaseTemperature = 41 };
Console.WriteLine(growingDegreeDays);

Amplíe esa idea para calcular totales graduales a partir de segmentos de los datos de entrada:

// showing moving accumulation of 5 days using range syntax
List<CoolingDegreeDays> movingAccumulation = new();
int rangeSize = (data.Length > 5) ? 5 : data.Length;
for (int start = 0; start < data.Length - rangeSize; start++)
{
    var fiveDayTotal = growingDegreeDays with { TempRecords = data[start..(start + rangeSize)] };
    movingAccumulation.Add(fiveDayTotal);
}
Console.WriteLine();
Console.WriteLine("Total degree days in the last five days");
foreach(var item in movingAccumulation)
{
    Console.WriteLine(item);
}

Este enfoque es útil cuando se necesitan transformaciones mientras se conservan los valores originales.

Pasos siguientes