2009-01-29 5 views
3

j'ai une question sur le sens (évaluation) des variables booléennes dans les états de retour en Java.expressions booléennes en Java

Je sais que:

if (var) { ... } 

est le même que:

if (var==true) { ... } 

Dans le second cas, nous disons explicitement var == vrai, mais on n'a pas besoin de faire cela, parce que Java évalue var comme vrai de toute façon. J'espère avoir compris ce droit.

Ma question est: est-ce la même chose quand les variables booléennes sont retournées? Lorsque nous avons une déclaration de retour?

Par exemple, une tâche spécifie: la méthode looksBetter() ne renvoie true que si b < a. Ma solution a été:

public boolean looksBetter() { 
    if (b < a) { 
     return true; 
    } else { 
     return false; 
    } 
} 

La réponse simple est:

public boolean lookBetter() { 
     return b < a; 
} 

Ainsi, il semble que nous avons ici encore une fois cette hypothèse implicite que dans le cas b < un == vrai, le retour de la méthode est vrai. Je suis désolé ... cela semble très trivial, mais je ne suis pas d'accord avec ça, et je ne sais pas pourquoi. Je vous remercie.

Répondre

13

Ce n'est pas une "supposition implicite", c'est ce que fait le compilateur. Le b < a est juste une expression, la même que si elle était utilisée pour une instruction if. L'expression est évaluée à boolean, qui est ensuite renvoyée.

Également remarquable, vous semblez échanger boolean et Boolean comme s'ils sont identiques, mais ils ne le sont pas. boolean est le formulaire primitive tandis que Boolean est an Object qui enveloppe un boolean.

+0

Mais pour toutes fins utiles, en particulier avec l'auto-boxing, les primitives et les wrappers d'objets sont la même chose. – cdeszaq

+0

Je suis d'accord sur un point, mais il y a certainement une différence entre eux qui devrait être comprise, en particulier pour quelqu'un de nouveau à la langue. –

+3

Le seul gotcha avec l'approche "essentiellement la même chose" est l'utilisation de null. Les objets peuvent être NULL, les primitives ne le peuvent pas. Essayez l'auto-déballage d'un null. Pas exactement évident ce que l'exception signifie. – basszero

11

Oui, cela est vrai pour tous les booléens. Vous pouvez penser à if (expression) évaluant 'expression' pour voir si c'est 'vrai' ou 'faux'. Lorsque vous faites

if(b < a == true) 

il premiers tests pour voir si b < a et si elle est, il teste maintenant:

if(true == true) 

Il teste maintenant si vrai == vrai (ce qui fait évidemment). Java ne fait rien de difficile quand vous omettez l'extra '== true', il suffit d'effectuer un test de moins. Il n'y a aucune raison que vous ne pouviez pas dire:

if(((b < a == true) == true) == true) 

mais causerait Java d'effectuer un test supplémentaire à chaque fois qu'il voit un signe égal.

5

Ne compliquez pas inutilement votre code. Si vous ressentez le besoin de dire "un < b == true", vous pouvez suivre que son conflusion logique (conclusion + confusion) et dire "((((((((...(a<b) == true) == true).... == true)"

"a < b" est une expression booléenne. Si vous avez déjà un booléen, pourquoi le comparer à un autre booléen?Vous ne le faites pas plus booléen de cette façon.

0

Tout comme C++, chaque instruction a une valeur de retour, même des choses sur le côté gauche de l'opérateur. Certains des plus fous C++ que j'ai vus ont des opérations sur le côté gauche avec leurs résultats assignés.

Je trouve cela fonctionne mieux si je fais ce qui suit:

bool result = (b > a); 
return result; 

La raison étant que c'est est un peu plus facile à déboguer (dans presque tous les IDE). Je trouve que j'enveloppe toujours entre parenthèses, je ne sais pas trop pourquoi. Je pense qu'il garde les électrons variables au chaud pendant qu'ils dorment la nuit.

-2

Votre méthode fonctionnera, mais il peut être un peu difficile de savoir exactement ce qui devrait se passer, surtout si vous avez juste des variables nommées a et b. Vous voulez documenter la méthode et avoir des variables avec des noms propres. De même, si le code vous déroute juste après l'avoir écrit, pensez à quelqu'un qui viendra dans 6 mois et n'aura aucune idée de ce qui se passe. Une documentation et des commentaires appropriés aideront grandement.

1

Une condition Java nécessite une valeur booléenne. Si vous pouvez le mettre dans une instruction if, c'est déjà un booléen, et ne nécessite pas d'autre bidouillage si ce que vous voulez est un booléen.

En effet, les constructions comme value == true peuvent être difficiles. Je ne me souviens pas des règles de promotion en Java, mais en C++ un bool peut être promu en int, avec false devenant 0 et vrai devenant 1. Par conséquent, int a = 2; if (a) et int a = 2; if (a == true) feront des choses différentes.

+0

Java n'a pas de règles de promotion. 'if (a)' et 'if (a == true)' vous donneront une erreur de compilation en Java. – Patrick

0

Je pense que vous demandez pourquoi vous rencontrez un problème conceptuel.

Je pense que le problème de base est que lorsque vous renvoyez directement une valeur booléenne, il vous manque quelque chose, et vous l'êtes. C'est le nom de la méthode dans votre cas.

Votre LooksBetter ne veut rien dire. Qu'est-ce que vous pensez vraiment est la suivante:

boolean isEarlier(Time a, Time b) { 
    if(a < b) //for simplicity let's ignore that this won't work. 
     return true; 
    else 
     return false; 
} 

Maintenant, vous pouvez réduire cela à:

boolean isEarlier=a < b; 

Hmm, eh bien maintenant, nous pouvons voir que est antérieure à b, et c'est ce que la valeur intermédiaire isEarlier signifie.

Donc une fois que vous internaliser type de cette valeur intermédiaire, ce qui rend plus de sens:

boolean isEarlier(Time a, Time b) { 
    return a < b; 
} 

Vous devez penser que « booléenne » comme une valeur réelle, et pas seulement un état intermédiaire. Si cela vous rend mal à l'aise, n'hésitez pas à en faire une variable (cela ne coûte rien, et peut le rendre plus lisible pour vous maintenant). Plus tard, vous regarderez votre code et serez plus à l'aise avec la façon plus courte de le regarder. Cela prend du temps à votre esprit pour développer de nouvelles voies, ne soyez pas gêné d'être explicite en attendant.

0

Ceci n'est pas une "supposition implicite" ou un autre type de magie.
Juste deux expressions différentes qui donnent le même résultat.
Il est quelque chose comme

int i = 123; 
return i; 

ou

int i = 123; 
return i + 0; 

"i" et "i + 0" sont deux expression qui donnent la même valeur. (Le compilateur devrait être assez intelligent pour simplifier le dernier dans le même que le premier)

1

Votre confusion pourrait être atténuée si vous essayez de considérer les opérateurs comme des méthodes. En utilisant votre exemple, vous avez eu l'opérateur < "inférieur à". Pour nos besoins, l'opérateur < peut vraiment être considéré comme une "méthode" (il ne ressemble qu'à un), qui prend deux paramètres et renvoie un résultat booléen. Si la « méthode » ont été nommés lessThan, votre exemple serait équivalent à ceci:

public boolean lookBetter() {  
    return lessThan(b, a);  
} 

Peut-être le voir comme ça fait un peu plus facile à comprendre? Incidemment, lorsque je dirigeais des groupes d'exercices dans le cours 'Programming 101' à Uni, cela s'est avéré être de loin la chose la plus difficile à enseigner, et beaucoup de gens ont eu du mal à saisir les concepts impliqués. Cela ressemblait presque à apprendre à faire du vélo ou à nager, une fois que vous avez compris comment cela fonctionne, cela devient évident d'une certaine façon.