Menu
CoddyTech

Validazione con i setter

Fa parte della sezione Programmazione orientata agli oggetti del percorso GDScript di Coddy. Lezione 27 di 65.

Un setter viene eseguito ogni volta che viene assegnato un valore alla sua proprietà, perciò è il punto in cui controllare il nuovo valore. Python genera un errore per un valore non valido. GDScript non ha eccezioni, quindi un setter fa invece una di queste cose: limita il valore all'intervallo consentito oppure mantiene il valore precedente e registra cosa è andato storto.

# character.gd
class_name Character
extends RefCounted

var last_error: String = ""
var hp: int = 100:
	set(value):
		hp = clampi(value, 0, 100)
var nickname: String = "Player":
	set(value):
		if value.length() < 3:
			last_error = "Name too short"
			return
		last_error = ""
		nickname = value

clampi(value, 0, 100) restituisce value riportato nell’intervallo da 0 a 100. Nel setter di nickname, return esce prima dell’assegnazione, quindi il vecchio nome rimane e last_error spiega perché:

# main.gd
var hero := Character.new()
hero.hp = 250
print(hero.hp) # 100
hero.nickname = "Al"
print(hero.nickname) # Player
print(hero.last_error) # Nome troppo corto
hero.nickname = "Alice"
print(hero.nickname) # Alice

Il setter viene eseguito anche per le assegnazioni all'interno della classe, in _init() e in ogni metodo. Assegna gli argomenti del costruttore tramite la proprietà e verranno controllati anche loro:

func _init(start_hp: int) -> void:
	hp = start_hp # esegue il setter: Character.new(500) inizia con 100

All'interno del setter stesso, assegnare hp memorizza il valore senza richiamare il setter. L'unica assegnazione che ignora il setter è il valore iniziale nella dichiarazione (= 100), quindi quel valore deve essere valido di per sé.

challenge icon

Sfida

Facile

Aggiungi la convalida alla classe Thermostat in thermostat.gd con i setter:

  • target (inizia da 20) accetta solo valori da 10 a 30. Per qualsiasi altro valore mantiene il vecchio target e imposta last_error su Target must be between 10 and 30.
  • mode (inizia da off) accetta solo heat, cool e off. Per qualsiasi altro testo mantiene la vecchia modalità e imposta last_error su Unknown mode: seguito dal testo.
  • Un'assegnazione valida reimposta last_error su una stringa vuota.
  • _init(start_target) assegna start_target a target, così il setter lo controlla.

Il codice fornito legge il target iniziale, poi il numero di comandi e infine un comando per riga (target 25 o mode cool). Dopo aver creato il termostato e dopo ogni comando, stampa Rejected: e l'errore quando last_error non è vuoto, quindi stampa lo stato. Con il valore iniziale 22 e i comandi target 35 e mode cool stampa:

Target 22, mode off
Rejected: Target must be between 10 and 30
Target 22, mode off
Target 22, mode cool

Il tuo codice va in thermostat.gd. main.gd contiene il codice di input/output fornito e non può essere modificato.

Provalo tu

extends Node

func _ready():
	# Codice di input/output fornito: lascialo così com'è
	var thermostat := Thermostat.new(int(OS.read_string_from_stdin()))
	report(thermostat)
	var count := int(OS.read_string_from_stdin())
	for i in count:
		var parts := OS.read_string_from_stdin().split(" ")
		if parts[0] == "target":
			thermostat.target = int(parts[1])
		else:
			thermostat.mode = parts[1]
		report(thermostat)

func report(thermostat: Thermostat) -> void:
	if thermostat.last_error != "":
		print("Rejected: " + thermostat.last_error)
	print("Target %d, mode %s" % [thermostat.target, thermostat.mode])
quiz iconMettiti alla prova

Questa lezione include un breve quiz. Inizia la lezione per rispondere e tenere traccia dei tuoi progressi.

Tutte le lezioni di Programmazione orientata agli oggetti

Esercitati da solo: Compilatore GDScript online