33

割り当てを行わずに Java 三項演算を行う方法や、割り当てを偽造する方法はありますか?

一連の if/then/else を実行するときの簡潔な 3 項コードの外観が気に入っています。

ブール代数ステートメントに基づいて、2 つの void 関数のいずれかを呼び出せるようにしたいと考えています。

何かのようなもの:

(bool1 && bool2) ? voidFunc1() : voidFunc2();

私の関数は return 型なvoidので、割り当てでこれを偽造して機能させる方法があれば、それで問題ありません...その方法を知りたいのですが:)

4

4 に答える 4

29

いいえ、それはできません。仕様はそう言っています。

条件演算子には 3 つのオペランド式があります。? は 1 番目と 2 番目の式の間に表示され、: は 2 番目と 3 番目の式の間に表示されます。

最初の式は boolean または Boolean 型である必要があります。そうしないと、コンパイル時エラーが発生します。

2 番目または 3 番目のオペランド 式がvoidメソッドの呼び出しであることは、コンパイル時エラーです。

[編集]

リフレクションについて尋ねたので、ここに解決策があります。これはお勧めしません。ご要望があったので掲載します。

public class MyCall
{

    public void a(){System.out.println("a");}
    public void b(){System.out.println("b");}

    public static void main(String... args)
    {
        new MyCall().go();
    }

    public void go()
    {
        Class<? extends MyCall> class1 = this.getClass();
        Method aMethod = class1.getMethod("b", null);
        Method bMethod = class1.getMethod("a", null);
        Object fake = false ? aMethod.invoke(this, null) : bMethod.invoke(this, null);
        Object fake2 = true ? aMethod.invoke(this, null) : bMethod.invoke(this, null);
    }
}

結局のところ、簡潔にすることでコードの可読性が向上するかどうかを自問する必要があります (for-each ループを考えてみてください)。これらのソリューションのいずれも、コードの可読性を改善するものではありません。私があなたなら、むしろこれで行きます。

if(condition)
    a();
else
    b();

実際には、ループに 1 行しか含まれていない場合でも中かっこを含めることに賛成ですが、鮮明なコードを求めているので、上記のスニペットで十分です。

于 2013-04-12T17:09:52.763 に答える
12

いいえ、このようにすることはできません。

より多くのステートメントを作成したくない場合は、このスタイルを好むことができます。

if(bool1 && bool2) voidFunc1(); else voidFunc2();

三項演算子では、オペランドは非 void 式である必要があります。つまり、何らかの実際の価値を生み出さなければなりません。

于 2013-04-12T17:05:05.300 に答える
2

割り当てを行わずに Java 三項演算を行う方法や、割り当てを偽造する方法はありますか?

OK、次のようなステートメントを書くと:

    (bool1 && bool2) ? voidFunc1() : voidFunc2();

コードには 2 つの明確な問題があります。

  1. 条件式1の第 2 オペランドと第 3 オペランドは、 void メソッドを呼び出すことはできません。参照: JLS 15.25 .

  2. 代入式またはメソッド呼び出しまたはオブジェクト作成でない限り、式はステートメントではありません。参照: JLS 14.8

実際、これらの問題の 2 番目は構文エラーであり、主流の Java コンパイラは最初の問題ではなく、この問題を報告するはずです。最初の問題は、次のようなことをした場合にのみ明らかになります。

    SomeType dummy = (bool1 && bool2) ? voidFunc1() : voidFunc2();

また

    gobble((bool1 && bool2) ? voidFunc1() : voidFunc2());

wheregobbleは何もしないメソッドです...その引数の値を「消費」することを除いて。

私の知る限り、元の表現が受け入れられる文脈はありません。

voidただし、条件式で呼び出すことができるように関数をラップする方法があります。これが1つです:

 int dummy = (bool1 && bool2) ? 
     () -> {voidFunc1(); return 0;} : 
     () -> {voidFunc2(); return 0;};

1 - 「条件式」は、Java 言語仕様でこの構造に使用される主な用語です。これは、Oracle Java チュートリアルでは「三項条件演算子」と呼ばれています。

于 2016-03-17T10:58:22.733 に答える