Semplici commenti Getter / Setter


125

Quale convenzione usi per commentare getter e setter? Questo è qualcosa che mi chiedo da un po 'di tempo, ad esempio:

/**
 * (1a) what do you put here?
 * @param salary (1b) what do you put here?
 */
public void setSalary(float salary);

/*
 * (2a) what do you put here?
 * @return (2b)
 */
public float getSalary();

Trovo sempre che sto scrivendo più o meno la stessa identica cosa per 1a / be 2a / b, qualcosa come 1a) Imposta lo stipendio del dipendente, 1b) lo stipendio del dipendente. Sembra così ridondante. Ora potrei vedere per qualcosa di più complesso che potresti scrivere di più nelle parti (a), per dare un contesto, ma per la maggior parte dei getter / setter là fuori la formulazione è quasi esattamente la stessa.

Sono solo curioso se, per i semplici getter / setter, va bene compilare solo la parte (a) OPPURE la parte (b).

Cosa ne pensi?


54
Per inciso, per favore non usare il float per nulla di monetario (come lo stipendio qui), mai. Si veda ad esempio stackoverflow.com/questions/965831/...
Jonik

3
Usa invece BigDecimal.
Josep

Risposte:


84

Di solito riempio solo la parte param per i setter e la parte @return per i getter:

/**
 * 
 * @param salary salary to set (in cents)
 */
public void setSalary(float salary);

/**
 * @return current salary (in cents, may be imaginary for weird employees)
 */
public float getSalary();

In questo modo gli strumenti di controllo javadoc (come gli avvisi di Eclipse) risulteranno puliti e non ci saranno duplicazioni.


Puoi correggere l'errore di battitura? "@return part for setters"
Jonik,

1
C'è anche un errore di battitura nel commento di salary (). Non è un commento JavaDoc.
Fostah

1
Sono d'accordo che sia l'approccio migliore per commentare gli accessori.
Fostah

31
Aggiungere rumore al tuo codice per silenziare un avvertimento eccessivamente pedante dai nostri strumenti mi sembra sbagliato. Se non aggiunge valore a un programmatore, la soluzione giusta sarebbe quella di abbassare / correggere la verbosità degli strumenti e / o diminuire quanto ci interessa fare i salti mortali in modo che gli strumenti ci ricompensino. Gli strumenti di analisi dovrebbero aiutarci e risparmiare fatica, non creare compiti più insensati per noi.
Lyle

1
@ Lyle Potrebbe essere vero, ma mi sembra che ci sia quasi sempre qualcosa di utile che un programmatore può dire che descrive un getter / setter meglio della sola firma del metodo. Sì, ci sono casi in cui un programmatore è pigro e ripete semplicemente la firma del metodo nel commento, ma penso che in generale sia un comportamento utile da forzare.
Matt Vukas

174

Assolutamente inutile: stai meglio senza questo tipo di schifezze che ingombra il tuo codice:

/**
 * Sets the foo.
 * 
 * @param foo the foo to set
 */
public void setFoo(float foo);

Molto utile, se garantito:

/**
 * Foo is the adjustment factor used in the Bar-calculation. It has a default
 * value depending on the Baz type, but can be adjusted on a per-case base.
 * 
 * @param foo must be greater than 0 and not greater than MAX_FOO.
 */
public void setFoo(float foo);

Soprattutto la spiegazione del significato effettivo della proprietà può essere cruciale nei modelli di dominio. Ogni volta che vedo un fagiolo pieno di proprietà con nomi oscuri che solo banchieri di investimento, biochimici o fisici quantistici capiscono, e i commenti spiegano che il metodo setGobbledygook () "imposta il gobbledygook.", Voglio strangolare qualcuno.


2
I miei sentimenti esattamente, i peggiori sono i modelli specifici del dominio in cui solo un esperto del dominio sa cosa diavolo significa la proprietà.
ThaDon,

7
Anche se è utile cosa faresti per getFoo (). Copierete lo stesso commento anche per getFoo ()?
Vinoth Kumar CM

3
@cmv: Ovviamente la parte "param" non verrebbe copiata. Sono indeciso se il valore di avere le informazioni allegate a entrambi gli accessori giustifica direttamente la duplicazione delle informazioni. Probabilmente sì. Ancora meglio sarebbe un modo per allegare un commento a entrambi; Credo che questo sia disponibile in Project Lombok.
Michael Borgwardt

@VinothKumar: forse sarebbe più bello spiegare semplicemente la proprietà nel getter (come in "Foo è il fattore di aggiustamento utilizzato nel calcolo della barra") e gli effetti della modifica del valore nel setter (o se è necessario o non inizializzare quel valore - nell'esempio della risposta non è necessario inizializzare Foo poiché "ha un valore predefinito che dipende dal tipo di Baz").
freitass

+1 per "nomi oscuri che solo banchieri di investimento, biochimici o fisici quantistici capiscono"
Jackson

36

Generalmente niente, se posso evitarlo. Getter e setter dovrebbero essere autoesplicativi.

So che suona come una non risposta, ma cerco di usare il mio tempo per commentare cose che necessitano di spiegazioni.


5
Un'altra valida risposta in questo senso potrebbe essere "i progetti con getter e setter non comprendono correttamente la nozione di incapsulamento" :)
Trejkaz

2
@Trejkaz: non vero, perché i metodi di accesso consentono proprietà di sola lettura o di sola scrittura e polimorfismo (e quindi wrapping, proxy e così via).
Laurent Pireyn

2
Possono consentire queste cose, ma spesso un modello builder può sostituire i setter (meno mutabili) o un modello visitatore può sostituire i getter (più flessibili)
Trejkaz

Certamente mi piace e utilizzo il pattern builder, ma c'è così tanto supporto per i POJO (ad esempio in Hibernate) che getter e setter hanno ancora il loro posto molto prominente, nel bene e nel male. È la cosa più brutta di Java, IMHO, e dopo aver scritto JavaDoc ripetitivi per oltre un decennio, sono quasi pronto per iscrivermi al consiglio di @ sleske.
Michael Scheper

34

Direi che ti preoccupi solo di commentare getter e setter se hanno una sorta di effetto collaterale o richiedono una sorta di precondizione al di fuori dell'inizializzazione (ad esempio: ottenere rimuoverà un elemento da una struttura dati o per impostare qualcosa di cui hai bisogno avere xey al loro posto per primi). Altrimenti i commenti qui sono piuttosto ridondanti.

Modifica: Inoltre, se trovi che molti effetti collaterali sono coinvolti nel tuo getter / setter, potresti voler cambiare il getter / setter per avere un nome di metodo diverso (ad esempio: push e pop per uno stack) [Grazie per i commenti sotto]


10
probabilmente, dovresti cambiare il nome dei getter che hanno effetti collaterali per essere più chiari, poiché non tutti gli sviluppatori leggeranno i commenti.
akf

Va bene, ma ciò richiede agli utenti della tua API di sapere che, se ci fossero stati effetti collaterali, sarebbero stati documentati !
oxbow_lakes

akf, stavo pensando esattamente che dopo aver postato :) Credo che lo aggiungerò alla mia risposta.
Gopherkhan

1
ma se non documenti getter e setter "stupidi" (è quello che preferisco anche io!) - come sbarazzarsi degli avvisi di Eclipse sulla mancanza di javadoc? Non voglio ingombrare il mio spazio di lavoro con avvisi del genere, ma non voglio che l'avviso venga disabilitato per tutti gli altri metodi ...
Zordid

12

Chiediti cosa vuoi che le persone vedano quando i commenti vengono visualizzati come JavaDoc (da un browser). Molte persone dicono che la documentazione non è necessaria poiché è ovvio. Questo non vale se il campo è privato (a meno che tu non attivi esplicitamente JavaDocs per i campi privati).

Nel tuo caso:

public void setSalary(float s)
public float getSalary()

Non è chiaro in che stipendio sia espresso. Sono centesimi, dollari, sterline, RMB?

Quando si documentano setter / getter, mi piace separare il cosa dalla codifica. Esempio:

/**
 * Returns the height.
 * @return height in meters
 */
public double getHeight()

La prima riga dice che restituisce l'altezza. Il parametro di ritorno documenta che l'altezza è in metri.


1
anche se sono d'accordo con te, penso che sia necessario assicurarsi che i commenti della funzione non stiano cercando un nome di funzione scelto male e non esplicito.
karlipoppins

Sono un grande sostenitore di JavaDocs, ma anche un grande sostenitore del codice auto-documentante. Quindi, almeno per il setter, farei qualcosa di simile public void setSalary(float aud)(o più realisticamente public void setSalary(BigDecimal aud)). Meglio ancora, la proprietà dovrebbe essere del tipo abstract class CurrencyAmount, che a sua volta ha le proprietà java.util.Currency currencye java.math.BigDecimal amount. La maggior parte degli sviluppatori con cui ho lavorato è terribilmente pigra con JavaDoc, ma l'applicazione di API come questa rende questo meno un problema.
Michael Scheper

Se l'unità è un'unità SI come metri / secondi, c'è meno bisogno di documentare, se non è un'unità Si allora deve essere documentata o meglio denominata per includere l'unità non standard, ad esempio heightFeet
AlexWien

8

Perché non includono solo un tag di riferimento per consentire di commentare il valore del campo e il riferimento da getter e setter.

/**
* The adjustment factor for the bar calculation.
* @HasGetter
* @HasSetter
*/
private String foo;

public String getFoo() {
  return foo;
}

public void setFoo() {
  this foo = foo;
}

In modo che la documentazione si applichi al getter e al setter oltre che al campo (se javadocs privato è attivato).


Sono d'accordo. E poi ho capito, perché scrivere comunque tutto questo boilerplate? Vedi la mia risposta sul Progetto Lombok.
Michael Scheper

7

Questo tipo di boilerplate può essere evitato utilizzando Project Lombok . Basta documentare la variabile di campo, anche se lo èprivate , e lascia che le annotazioni di Lombok generino getter e setter adeguatamente documentati.

Per me, questo vantaggio da solo vale i costi .


4

Sono davvero deluso dalle risposte che sostanzialmente dicono che una documentazione completa è una perdita di tempo. In che modo i client della tua API dovrebbero sapere che un metodo chiamato setXè un setter di proprietà JavaBean standard a meno che tu non lo dica chiaramente nella documentazione ?

Senza documentazione, un chiamante non avrebbe idea se il metodo avesse effetti collaterali, a parte l'incrocio delle dita sull'apparente convenzione seguita.

Sono sicuro di non essere l'unico qui ad aver avuto la sfortuna di scoprire nel modo più duro che un metodo chiamato setXfa molto di più che impostare una proprietà.


11
Senza documentazione, qualsiasi chiamante presumerebbe che un metodo chiamato setX imposta X. Ne consegue che se setX imposta effettivamente X, senza fare nient'altro di importante, allora non hai bisogno di documentazione.
mqp

È fantastico! Ora questa azienda CrudTech, la cui API sto codificando contro, segue la tua convenzione o segue quella di qualcun altro su questo thread? Hmmmm
oxbow_lakes

5
Non ha senso scrivere "imposta il prezzo" nel documento setPrice se il metodo imposta solo il valore per la proprietà price, ma se ad esempio aggiorna anche la proprietà totalPrice e ricalcola la tassa, tale comportamento dovrebbe ovviamente essere documentato.
João Marcus

8
Sembra che tu stia chiedendo che la documentazione dichiari "Questo fa quello che ti aspetti". Che è un po 'come scrivere "Attenzione: CALDO" su una tazza di caffè. In un mondo perfetto, non ci sarebbe bisogno di dire mai cose del genere.
Kevin Panko

1
Sì, avendo utilizzato API in cui metodi chiamati cose come setXavevano effetti collaterali diversi da quelli attesi, posso effettivamente affermare con sicurezza che questo non è un mondo perfetto.
oxbow_lakes

4

Se non ci sono operazioni speciali in getter / setter di solito scrivo:

Con Javadoc (con opzione privata):

/** Set {@see #salary}. @param {@link #salary}. */
public void setSalary(float salary);

e / o

/** 
 * Get {@see #salary}.
 * @return {@link #salary}.
 */
public float salary();

Con Doxygen (con opzione di estrazione privata):

/** @param[in] #salary. */
public void setSalary(float salary);

/** @return #salary. */
public float salary();

2
Il problema con questo approccio è che Javadoc non genera la documentazione privata per impostazione predefinita! In tal caso, il tag di riferimento {@see #salary}non è valido nella documentazione generata.
Jarek Przygódzki

1

Commentare le funzioni di accesso, soprattutto se non eseguono alcuna operazione da nessuna parte, è inutile e uno spreco di dita.

Se qualcuno che legge il tuo codice non riesce a capirlo person.getFirstName() restituisce il nome di una persona, dovresti provare tutto ciò che è in tuo potere per farlo licenziare. Se fa un po 'di magia nel database, lancia alcuni dadi, chiama il Segretario dei nomi per ottenere il nome, è lecito ritenere che sia un'operazione non banale e documentarla bene.

Se, d'altra parte, il tuo person.getFirstName()non restituisce il nome di una persona ... beh, non andiamo lì, vero?


6
Cosa succede se getFirstName () restituisce null? Dove sarebbe documentato?
Steve Kuo

Che ne dici di security.getFinalMaturity ()? Non tutti i nomi di proprietà hanno un significato immediatamente comprensibile. Vorresti essere licenziato per non sapere cosa significa?
Michael Borgwardt

E se il metodo fosse implementato tramite swizzling? Come dovresti saperlo a meno che non sia stato chiaramente documentato? Come fai a sapere che è uno standard setter a meno che il dottore non dica che lo è?
oxbow_lakes

2
get / set dovrebbe a mio parere essere riservato a getter e setter. Le ricerche nel database dovrebbero essere denominate come "lookupPerson" o giù di lì.
Thorbjørn Ravn Andersen

1

Non inserire nulla se il nome del campo è sufficientemente descrittivo del contenuto.

In generale, lascia che il codice sia autonomo ed evita di commentare se possibile. Ciò potrebbe richiedere il refactoring.

EDIT: Quanto sopra si riferisce solo a getter e setter. Credo che qualsiasi cosa non banale dovrebbe essere correttamente javadoc'ed.


1
C'è una differenza tra commentare e documentare.
Tom Hawtin - tackline

1
Verissimo. Proprio per questo motivo non commento getter e setter. Dovrebbero essere autoesplicativi e l'aggiunta di un commento indica che il codice non è autoesplicativo.
Thorbjørn Ravn Andersen

0

va bene compilare la parte (b), soprattutto se si inserisce un commento nella dichiarazione del campo indicando di cosa tratta il campo.


Non va bene - le persone non leggono i commenti sul campo. Javadoc non genera nemmeno la documentazione privata per impostazione predefinita e gli IDE non mostrano la documentazione sul campo quando si utilizza la guida rapida su una chiamata al metodo.
Trejkaz

le persone non leggono i commenti sul campo a meno che non sia necessario. Una volta che c'è bisogno, maggiori sono le informazioni, meglio è.
akf

0

Se javadoc non aggiunge nulla, elimino javadoc e utilizzo i commenti generati automaticamente.


0

Compilo sempre entrambi. Il tempo aggiuntivo dedicato alla digitazione è trascurabile e più informazioni sono meglio di meno, in generale.


Sono solo autoesplicativi se dici "questo è un responsabile della proprietà". Altrimenti un client dell'API non ha idea di cosa stia realmente accadendo all'interno dei metodi
oxbow_lakes,

1
Chi ha parlato di autoesplicativo?
Paul Sonier
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.