Track
/
Crystal
Crystal
/
Esercizi
/
La bilancia
La bilancia

La bilancia

Esercizio di apprendimento

Introduzione

I getter e i setter sono metodi che ti permettono di leggere e scrivere il valore di una proprietà di un oggetto. Crystal ha le macro, che rendono semplice definire getter e setter per una proprietà. Le macro sono un modo per generare codice in fase di compilazione; ne parleremo più avanti nel concetto dedicato alle macro.

In Ruby questi metodi si definiscono con i metodi attr_reader, attr_writer e attr_accessor e, in superficie, sono molto simili all'implementazione di Crystal. In Crystal sono state definite come le macro getter, setter e property.

Getter

Getter è una macro che definisce un metodo che restituisce il valore di una variabile di istanza. Questo significa che non devi più scrivere @ davanti alla variabile di istanza quando vuoi accedervi (nei metodi, escluso initialize); puoi invece chiamare il metodo definito dalla macro getter.

La macro getter può accettare più variabili di istanza, separandole con delle virgole.

# This:
class Person
  @name : String
  @age : Int32

  def name
    @name
  end

  def age
    @age
  end
end

# Is the same as this:
class Person
  @name : String
  @age : Int32

  getter name, :age
end

Come puoi vedere, usare getter riduce la quantità di codice da scrivere e lo rende più facile da leggere. Inoltre, Ruby e Crystal differiscono in un punto: Crystal accetta come argomenti della macro getter sia il nome della variabile sia il simbolo. I simboli saranno trattati più avanti, nel concetto dedicato ai simboli.

Setter

Setter è una macro che definisce un metodo che imposta il valore di una variabile di istanza. Questa macro non si incontra spesso: al suo posto si usa di solito la macro property. I metodi che verranno creati avranno una forma del tipo name_of_method=; è il segno = che permette di impostare la proprietà.

Questa definizione di metodo è un po' particolare, perché l'argomento che il metodo riceve sta dopo il segno =. Anche altri metodi speciali di Crystal usano questa sintassi, come il metodo +.

Come per la macro getter, quando vuoi aggiornare il valore di una variabile di istanza dopo aver definito un setter, puoi chiamare il metodo definito dalla macro setter.

# This:
class Person
  @name : String
  @age : Int32

  def name=(name : String)
    @name = name
  end

  def age=(age : Int32)
    @age = age
  end
end

# Is the same as this:
class Person
  @name : String
  @age : Int32

  setter name, :age
end

Property

Property è una macro che definisce sia un getter che un setter per una variabile di istanza.

class Person
  @name : String
  @age : Int32

  property name, :age
end

Istruzioni

In questo esercizio modelleremo una bilancia.

1. Creare uno stato iniziale per la bilancia

Quando viene inizializzata, la bilancia dovrebbe fare riferimento alle proprie impostazioni di fabbrica, che sono diverse a seconda di dove viene venduta. Di conseguenza, la macchina dovrebbe poter essere inizializzata con una precisione e specificando se usa il sistema metrico o quello imperiale.

Implementa il metodo WeighingMachine#initialize, che accetta due argomenti: precision, che è un Int32, e metric, che è un Bool. L'argomento metric, quando è true, indica che la macchina deve usare il sistema metrico, altrimenti deve usare il sistema imperiale. Il metodo initialize dovrebbe anche impostare la variabile di istanza @weight a 0.0.

precision = 3
metric = true
vm = WeighingMachine.new(precision, metric)

2. Consentire alla bilancia di avere una precisione

Per soddisfare esigenze diverse, permettiamo di personalizzare ogni bilancia con una precisione (il numero di cifre dopo il separatore decimale).

Implementa il metodo getter WeighingMachine#precision in modo che restituisca la precisione della bilancia.

precision = 3
metric = true
vm = WeighingMachine.new(precision, metric)
vm.precision
# => 3

3. Consentire di impostare il peso sulla bilancia

Implementa la proprietà WeighingMachine#weight per poter ottenere e impostare il peso:

precision = 3
metric = true
wm = WeighingMachine.new(precision, metric)
wm.weight = 60.5
wm.weight
# => 60.5

wm.weigh
# => 60.5

4. Consentire di passare tra unità metriche e imperiali sulla macchina

Implementa la proprietà WeighingMachine#metric= per consentire di impostare l'unità. Dovrebbe accettare un valore booleano.

precision = 3
metric = true
wm = WeighingMachine.new(precision, metric)
vm.weight = 60.5
wm.metric = false

vm.weigh
# => 133.377
Modifica tramite GitHub Il link si apre in una nuova finestra o scheda
Crystal Exercism

Vuoi iniziare La bilancia?

Iscriviti a Exercism per imparare e padroneggiare Crystal con 26 concetti142 esercizi e il mentoring di persone reali, tutto gratis.