Menu
Coddy logo textTech

Getters y Setters

Parte de la sección Programación Orientada a Objetos del Journey de Dart de Coddy — lección 21 de 110.

Los getters y setters proporcionan una forma de acceder y modificar los campos de una clase a través de métodos especiales que parecen propiedades regulares. En lugar de exponer los campos directamente, puedes controlar cómo se leen y escriben los valores.

Un getter se define utilizando la palabra clave get y devuelve un valor calculado o almacenado:

class Rectangle {
  double width;
  double height;
  
  Rectangle(this.width, this.height);
  
  double get area => width * height;
  double get perimeter => 2 * (width + height);
}

Rectangle rect = Rectangle(5, 3);
print(rect.area);      // 15.0
print(rect.perimeter); // 16.0

Observa que area y perimeter se acceden como campos, pero se calculan cada vez. No se necesitan paréntesis.

Un setter utiliza la palabra clave set y te permite controlar cómo se asigna un valor:

class Temperature {
  double _celsius;
  
  Temperature(this._celsius);
  
  double get celsius => _celsius;
  set celsius(double value) {
    if (value >= -273.15) {
      _celsius = value;
    }
  }
  
  double get fahrenheit => _celsius * 9 / 5 + 32;
  set fahrenheit(double value) {
    celsius = (value - 32) * 5 / 9;
  }
}

Temperature temp = Temperature(25);
print(temp.fahrenheit);  // 77.0
temp.fahrenheit = 100;
print(temp.celsius);     // 37.78

El setter valida la entrada antes de almacenarla e incluso puede convertir entre unidades. Esto te da control sobre tus datos mientras mantienes una sintaxis limpia, similar a una propiedad, para los usuarios de tu clase.

challenge icon

Desafío

Fácil

Vamos a construir un rastreador de puntuación para un juego que utiliza getters y setters para gestionar las estadísticas del jugador con validación y valores calculados.

Organizarás tu código en dos archivos:

  • player.dart: Define una clase Player que rastree el rendimiento de un jugador en el juego. Tu clase debe tener:
    • Un campo String name para el nombre del jugador
    • Un campo privado int _score que comience en 0
    • Un campo privado int _lives que comience en 3
    • Un constructor que reciba el nombre del jugador
    • Un getter score que devuelva la puntuación actual
    • Un setter score que solo acepte valores de 0 o superiores (ignora los valores negativos)
    • Un getter lives que devuelva las vidas actuales
    • Un setter lives que solo acepte valores entre 0 y 5 inclusive (ignora los valores fuera de este rango)
    • Un getter level que calcule el nivel del jugador basándose en la puntuación: la puntuación dividida por 100 (división entera), más 1
    • Un getter isAlive que devuelva true si las vidas son mayores que 0
    • Un método displayStatus() que imprima el estado actual del jugador
  • main.dart: Importa tu clase de jugador y demuestra el funcionamiento de los getters y setters:
    • Crea un jugador llamado 'Alex'
    • Establece la puntuación en 250 y llama a displayStatus()
    • Intenta establecer la puntuación en -50 (debe ser ignorado) y llama a displayStatus()
    • Establece las vidas en 1 y llama a displayStatus()
    • Intenta establecer las vidas en 10 (debe ser ignorado) y llama a displayStatus()

El método displayStatus() debe imprimir exactamente en este formato:

[name] | Score: [score] | Level: [level] | Lives: [lives] | Alive: [isAlive]

Salida esperada:

Alex | Score: 250 | Level: 3 | Lives: 3 | Alive: true
Alex | Score: 250 | Level: 3 | Lives: 3 | Alive: true
Alex | Score: 250 | Level: 3 | Lives: 1 | Alive: true
Alex | Score: 250 | Level: 3 | Lives: 1 | Alive: true

Hoja de referencia

Los getters y setters proporcionan un acceso controlado a los campos de la clase a través de métodos especiales que parecen propiedades normales.

Getter - definido mediante la palabra clave get, devuelve un valor calculado o almacenado:

class Rectangle {
  double width;
  double height;
  
  Rectangle(this.width, this.height);
  
  double get area => width * height;
  double get perimeter => 2 * (width + height);
}

Rectangle rect = Rectangle(5, 3);
print(rect.area);      // 15.0 - se accede como un campo, sin paréntesis
print(rect.perimeter); // 16.0

Setter - utiliza la palabra clave set, controla cómo se asignan los valores:

class Temperature {
  double _celsius;
  
  Temperature(this._celsius);
  
  double get celsius => _celsius;
  set celsius(double value) {
    if (value >= -273.15) {
      _celsius = value;
    }
  }
  
  double get fahrenheit => _celsius * 9 / 5 + 32;
  set fahrenheit(double value) {
    celsius = (value - 32) * 5 / 9;
  }
}

Temperature temp = Temperature(25);
print(temp.fahrenheit);  // 77.0
temp.fahrenheit = 100;
print(temp.celsius);     // 37.78

Los setters pueden validar la entrada y convertir entre unidades mientras mantienen una sintaxis limpia, similar a la de una propiedad.

Pruébalo tú mismo

import 'player.dart';

void main() {
  // TODO: Crea un jugador llamado 'Alex'

  // TODO: Establece el score a 250 y llama a displayStatus()

  // TODO: Intenta establecer el score a -50 (debería ser ignorado) y llama a displayStatus()

  // TODO: Establece lives a 1 y llama a displayStatus()

  // TODO: Intenta establecer lives a 10 (debería ser ignorado) y llama a displayStatus()
}
quiz iconPonte a prueba

Esta lección incluye un breve cuestionario. Empieza la lección para responderlo y registrar tu progreso.

Todas las lecciones de Programación Orientada a Objetos