2013-12-18 21 views
5

Ho una domanda sui valori booleani in Java. Diciamo che ho un programma come questo:Cambia valori booleani?

boolean test = false; 
... 
foo(test) 
foo2(test) 

foo(Boolean test){ 
    test = true; 
} 
foo2(Boolean test){ 
    if(test) 
    //Doesn't go in here 
} 

Ho notato che in foo2, il test booleano non cambia e quindi non va in l'istruzione if. Come farei allora a cambiarlo? Ho esaminato i valori booleani ma non sono riuscito a trovare una funzione che avrebbe "impostato" il test da vero a falso. Se qualcuno potesse aiutarmi sarebbe fantastico.

+2

Java è passato per valore. Rendi la variabile una variabile di istanza e modificala e controllala. –

+0

@SotiriosDelimanolis Sì. Ma il valore di un java.lang.Object (e sottotipi, cioè qualsiasi tipo non primitivo) è l'indirizzo di riferimento. –

+0

@ElliottFrisch Non vedo dove arriva _but_ –

risposta

4

si sta passando il valore di un valore booleano primitiva alla funzione, non v'è alcun "riferimento". Quindi stai solo oscurando il valore all'interno del tuo metodo foo. Invece, si potrebbe desiderare di utilizzare uno dei seguenti -

Un Holder

public static class BooleanHolder { 
    public Boolean value; 
} 

private static void foo(BooleanHolder test) { 
    test.value = true; 
} 

private static void foo2(BooleanHolder test) { 
    if (test.value) 
    System.out.println("In test"); 
    else 
    System.out.println("in else"); 
} 

public static void main(String[] args) { 
    BooleanHolder test = new BooleanHolder(); 
    test.value = false; 
    foo(test); 
    foo2(test); 
} 

quali uscite "In prova".

Oppure, utilizzando una variabile membro

private boolean value = false; 

public void foo() { 
    this.value = true; 
} 

public void foo2() { 
    if (this.value) 
    System.out.println("In test"); 
    else 
    System.out.println("in else"); 
} 

public static void main(String[] args) { 
    BooleanQuestion b = new BooleanQuestion(); 
    b.foo(); 
    b.foo2(); 
} 

Quale, emette anche "Nel test".

+0

Con l'approccio Holder, dovresti creare un nuovo file chiamato BooleanHolder, perché è pubblico? – user1871869

+0

L'ho scritto con una [Nested Class] (http://docs.oracle.com/javase/tutorial/java/javaOO/nested.html), ma potevi (ma non sarebbe stata una classe nidificata statica) . –

1

Hai chiamato il tuo parametro come una variabile di istanza. Qui, il parametro è quello a cui si fa riferimento, non la variabile di istanza. Questo è chiamato "shadowing", dove il nome semplice test come nome parametro ombreggia la variabile di istanza chiamata anche test.

In foo, è cambiato il parametro test a true, non l'istanza variabile test, che è rimasta invariata. Questo spiega perché non entra nel blocco if in foo2.

Per assegnare il valore, eliminare il parametro su foo o utilizzare this.test per fare riferimento alla variabile di istanza.

this.test = true; 

e

if (this.test) 
+0

Hm, con questo metodo viene visualizzato un errore che dice: errore: variabile non statica non può essere referenziata da un contesto stico – user1871869

0

Il metodo foo ha modificato il valore di test in true. Sembra che quello che vuoi è usare variabili di istanza per ogni funzione.

boolean test = false; 
... 
foo(test) 
foo2(test) 

foo(Boolean test){ 
    this.test = true; 
} 
foo2(Boolean test){ 
    if(this.test) 
    //Doesn't go in here 
} 

In questo modo, il metodo cambia solo il valore del test all'interno di tale metodo, ma il vostro parametro pubblica test rimane con un valore false.

1

Devi essere consapevole del fatto che:

  1. In Java, gli argomenti sono pass-by-value.
  2. booleano, il tipo di wrapper di booleano, è immutabile.

A causa di 1 e 2, non è possibile modificare lo stato del passaggio booleano nel metodo.

È in gran parte ha 2 scelta:

Scelta 1: Avere un supporto mutabile per booleano come:

class BooleanHolder { 
    public boolean value; // better make getter/setter/ctor for this, just to demonstrate 
} 

modo nel codice dovrebbe assomigliare:

void foo(BooleanHolder test) { 
    test.value=true; 
} 

Scelta 2: Una scelta più ragionevole: restituire il valore dal metodo:

boolean foo(boolean test) { 
    return true; // or you may do something else base on test or other states 
} 

il chiamante deve utilizzarlo come:

boolean value= false; 
value = foo(value); 
foo2(value); 

Questo approccio è preferibile in quanto si adattano meglio con le normali pratiche di codifica Java, e la firma del metodo dà suggerimento per il chiamante che sta andando per restituirti una nuova base di valori sul tuo input