2017-09-04 1 views
1

J'ai ce code ici et essaie d'utiliser:Quand dois-je utiliser ceci dans une méthode?

public class RationalNumber() { 
    private int num; 
    private int den; 

    public RationalNumber(int n, int d) { 
     num = n; 
     den = d; 
    } 

    public void multiply(RationalNumber r) { 
     /* missing code */ 
    } 

    public int getNum() { 
     return num; 
    } 

    public int getDen() { 
     return den; 
    } 
} 

Dans la méthode de multiplication public void, j'ai besoin multiplier méthode pour multiplier le numérateur du nombreRationnel par le numérateur de r, et le dénominateur de cette RationalNumber par le dénominateur de r. Lequel des éléments suivants peut être utilisé pour remplacer/* code manquant */de sorte que le multiplier().

Je l'ai réduit à:

num = num * r.num; 
den = den * r.den; 

ou

this.num = this.num * r.num; 
this.den = this.den * r.den; 

ou

num = num * r.getNum(); 
den = den * r.getDen(); 

Quelqu'un pourrait-il me dire quel un de ces (ou plus d'un) obtenir la méthode pour fonctionner comme prévu?

+1

Pourquoi ne pas les essayer et voir? – OldProgrammer

+1

Juste pour chuck dans une quatrième/cinquième manière: 'num * = r.num;' ou 'num * = r.getNum();'. –

Répondre

1

Je pense que le dernier fonctionnera comme prévu:

num = num * r.getNum(); 
den = den * r.getDen(); 
+2

Alors faites les autres. – Andreas

+0

Oui, vous avez raison toutes les méthodes de travail;) – Dayana

2

Les trois voies sont Corret, depuis:

1. num = num * r.num; 
2. den = den * r.den; 

Ligne 1: assigne num (variable d'instance) * r.num (variable d'instance de r) résultat à num. Même num ou den ayant un accès privé, lorsque vous traitez avec la même classe à l'intérieur de lui-même, vous êtes en mesure d'accéder aux membres privés.

Ligne 2: assigne den (variable d'instance) * r.den (variable d'instance de r) résultat à den.

this.num = this.num * r.num; 
this.den = this.den * r.den; 

Dans ce code, vous utilisez le mot-clé this dire explicetely que le num et den sont variables d'instance de la classe. Dans ce cas, ce n'est pas nécessaire, car vous n'avez pas d'observation (lorsqu'une variable locale ombrage le nom d'une variable d'instance). La logique est la même ci-dessus.

num = num * r.getNum(); 
den = den * r.getDen(); 

Vous utilisez juste une méthode accesseur (get) pour obtenir les valeurs des champs privés. La logique continue la même chose. Puisque, comme je l'ai déjà dit, l'objet courant peut accéder à des membres privés d'objets de la même classe, cela ne sera pas nécessaire.

j'utiliser la première manière dans ce cas;)

0

Essayez celui-ci, je pense qu'il est le plus correct formellement:

this.num = this.num * r.getNum(); 
this.den = this.den * r.getDen(); 
+0

Il n'est pas plus correct que les autres. Si vous pensez vraiment que c'est, expliquez pourquoi. – Andreas

+0

Je dirais parce que vous appelez getters sur le paramètre passé par l'appelant de la méthode, tandis que 'this.num' ou' this.den' clarifient que vous appelez des variables pour l'objet courant. Remarque Je parle de formalité. – leodali

2

Tous sont fonctionnellement équivalents.

Vous n'auriez besoin de this que si vous devez vous assurer que vous faites référence aux variables d'instance, au lieu de variables ou de paramètres locaux. Si votre constructeur avait params nommé num et den, vous devez écrire

this.num = num; 
this.den = den; 

pour spécifier que vous souhaitez affecter le param num à la variable d'instance num.

Cependant, comme il n'y a pas d'ambiguïté dans les méthodes, elles fonctionneront toutes. Vous pouvez également accéder directement aux variables r.num et r.den, car même si elles sont privées, elles restent accessibles à la même classe , et pas seulement à la même instance.

Je l'écris comme

num *= r.num; 
den *= r.den; 
+0

Ils ne sont pas tout à fait équivalents sur le plan fonctionnel: vous pouvez remplacer les getters d'une sous-classe pour faire quelque chose de différent: alors le 3ème sera différent du 1er et du second. Si vous faisiez la classe finale, ils seraient les mêmes. –

5

En bref: Tous les trois devraient fonctionner, il n'y a qu'une seule différence avec la dernière variante: Votre classe est pas définitive qui permet les sous-classes pour changer le comportement des getNum et getDen .

De même, il est assez rare de créer des classes représentant un nombre à être modifiable. Peut-être qu'il est préférable de changer la signature de multiply être

public RationalNumber multiply(RationalNumber) 

qui retourne une nouvelle RationalNumber avec le résultat de la multiplication au lieu de changer l'état interne de l'actuel. Dans ce cas, la mise en œuvre serait

return new RationalNumber(num * r.num, den * r.num); 

(ou toute autre variante que vous avez fourni)

1

En fait, il y a des opinions opposées: utiliser this pour la classe variable toujours, pour être sûr que cette variable appartient à. Ou un autre: en utiliser un s'il y a un conflit entre la variable locale et la variable de classe.

Dans mon travail, j'utilise le second: n'utilise this que si je le dois. Comme moins de mots dans le code, que possible - moins de problèmes. Donc, dans votre exemple, vous pouvez utiliser n'importe quelle variante.

0

Après la réponse de Lothar, il serait préférable que la méthode multiply retourne une nouvelle entité RationalNumber. Je rends même la méthode statique à la classe, puisqu'il s'agit d'une opération courante entre RationalNumber s, au lieu de quelque chose qui interagit avec une seule instance de la classe qui le modifie.

De cette façon, vous l'appelez comme ceci:

RationalNumber mul = RationalNumber.multiply(rn1,rn2); 

La définition de la méthode serait alors:

public static RationalNumber multiply(RationalNumber rn1, RationalNumber rn2){ 
    return new RationalNumber(rn1.getNum() * rn2.getNum(), rn1.getDen() * rn2.getDen()); 
} 
+0

Donc vous pensez aussi ['BigDecimal.multiply (BigDecimal multiplicand)'] (https://docs.oracle.com/javase/8/docs/api/java/math/BigDecimal.html#multiply-java.math.BigDecimal -) devrait être "statique"?Cela rendrait encore plus encombrant à utiliser, c'est-à-dire au lieu de 'bd1.multiply (bd2)', il faudrait écrire 'BigDecimal.multiply (bd1, bd2)'. – Andreas

+0

C'est un bon point et bien que je doive admettre qu'il est peu pratique à utiliser, je pense que cela pourrait être fait pour une raison plus importante, comme la sécurité des threads –

+0

Comment la méthode 'static' améliore-t-elle la sécurité des threads? Faire l'objet * immuable *, comme [Lothar suggéré] (https://stackoverflow.com/a/46043585/5221149), fait cela. Le rendre statique ne fait aucune différence fonctionnelle, mais le rend lourd à utiliser. – Andreas