2017-08-22 9 views
0

私はKotlinの初心者ですが、私はそれが大好きです。 3行のコードを1つにまとめると素晴らしい気分になります。今私はしばしば自分のコードを見て、「ここには冗長性があると思っています。それを行うためのより簡潔な方法が必要です。検索をすると、コトリンはより簡潔な方法を提供することがよくあります。if/else条件の戻り値だけでなく、実行コード

ここでは、シンプルで簡潔なKotlinソリューションがあるはずですが、それを認識していないと感じる問題があります。うまくいけば、あなたは私を啓発することができます!この不自然な例のように

テイクコード:if条件に基づいて

fun doSomething(): Boolean { 
    if (randomInt % 2 == 0) { 
     foo = Foo() 
     true 
    } else { 
     bar = null 
     false 
    } 
} 

、私はいくつかのコードを実行し、条件の値を返すようにしたいです。 「条件が真であれば、trueを返し、偽の場合はfalseを返してください」と明示的に言わなければならないということが私には気になります。それは冗長なようだ。もちろん、私はreturn randomInt % 2と言うことができますが、それが真である場合に基づいてコードを実行したいと思います。

私は知らない魔術師Kotlinはありますか?私のためにこの状況を処理する関数を作るべきですが、それを呼び出す構文はif文とは異なるでしょうか?何らかのマッピング関数がありますか、もしあれば、何らかの方法でオーバーロードできますか?簡潔で賢い答えがあるはずだが、それは私には来ない。

+0

私がJavaで知っている1行のみの解決策でこれをしたいのであれば、もしif、elseとwhileがサポートしていないなら、if条件ではなく、Kotlinの代入で代入されます。 – Avi

+0

ちょうど@ pixel-elephantの解決策に固執するすべてが良い古い方法を使用しないようにするには、新しい方法で解決しなければならない場合はごめんなさい – guenhter

+0

私は申し訳ありませんが、私は質問を投票したが、 "魔法のオペレーター"この特殊なケースは、 'randomInt%2 == 0'を変数に抽出することで解くことができます。これは、Java、Cおよび他の「古くて退屈な」言語と同じです。 Kotlinは魔法ではなく、Kotlinのコードは私たちが書いたほど良いものです。 – voddan

答えて

1

私はいくつかの回答をアップしました。私は条件を変数に分割するか、条件の後に真偽判定を行うべきだと考えていたはずです。

しかし、それを眠った後、別の解決策があります。

新しいユーティリティ機能:

fun Boolean.onTrue(block:() -> Unit): Boolean { 
    if (this) block() 
    return this 
} 

fun Boolean.onFalse(block:() -> Unit): Boolean { 
    if (!this) block() 
    return this 
} 

そして私の元のコードサンプルはに凝縮することができます:それは、独自の欠点を有しているが、

fun doSomething() = (randomInt % 2).onTrue { foo() }.onFalse { bar = null } 

これは最も簡潔なオプションです。ユーザーが例えばonTrue()を2回呼び出すこと、またはをonTrue()の前に呼び出すことはできません。 if/elseとはかなり違って見えますが、両方のパスを使用する場合は、onTrue()onFalse()の両方で条件を確認する必要があります。そして、もちろん、標準のKotlin演算子の代わりに新しいユーティリティ関数を使うことを覚えています。それでも、それは魅力的な簡潔さを持っています。私は他の人が何を考えているのか興味を持っています。

+0

これはジャークのように見えるかもしれませんが、考慮した後、私はこのアプローチを行っています。より簡潔で、冗長性が低く、より有用で、より多くの "Kotliny"私は感じる。それはコードレビューに合格しています(ただし、反対意見はありません)。私は既に輝いているいくつかのケースを発見しました。一般的にKotlinによく似ていますが、私はコードを単純化する方法が大好きです。 –

6

リターンとコードが異なる場所で起こるように、あなたはあなたのコードビットをリファクタリングすることができます

fun doSomething(): Boolean { 
    val isEven = randomInt % 2 == 0 

    if (isEven) foo = Foo() else bar = null 

    return isEven 
} 
+2

私はばかだと呼びますが、私は本当に他の答えを得ていません。どうしてあなたは 'true'と' false'を 'if'から返すように複雑にするのですか?この問題は、この答え(CとJavaで同じようにうまくいく)で示されるように、最初に存在してはならないはずです。 – voddan

1

あなたはKotlinのstandard libraryからいくつかの便利な拡張機能を探ることがあります。たとえば、あなたがapply使用することができます:ここで

/** 
* Calls the specified function [block] with `this` value as its receiver and returns `this` value. 
*/ 
public inline fun <T> T.apply(block: T.() -> Unit): T { block(); return this } 

を、randomInt % 2 == 0applyの戻り値になります。

fun doSomething(): Boolean = (randomInt % 2 == 0).apply { if (this) foo = Foo() else bar = null } 

アップデート:あなたがより読みやすいコードを希望する場合、それは良い解決策ではありません。楽しんでください:)

+0

これは良い説明ですが、目的を解決しませんでした。しかし、何か新しいことを学ぶupvoteに値する。 – Avi

+0

ひどく過小評価されています。簡単な答えは、結果を変数に格納することです。このすべての解決策は、あなたのコードを読みやすく保守しにくいものにします。 –

+0

@Gabe Sechan 'boolean'は受信側と関数の戻り値として機能し、' this'を使ってラムダ内の 'boolean'を参照します。それほど複雑ではありません。一直線になっているので複雑に感じるかもしれません。それを複数行のコードに分割すると読みやすくなります。 – BakaWaii

0

@ pixel-elephantのソリューションは簡潔で見栄えが良いようです。

ただし、クリーンコードの観点から、doSomething()関数は2つのことを行っています。

次の2つの関数にそれを分離し、最上位の関数にあればチェックを移動することができ可能であれば:

if (randomInt.isEven()) { 
    doSomethingEven() 
    // ... 
} else { 
    doSomethingOdd() 
    // ... 
} 
1

それはあなただけのようなKotlinの幻想STDLIB機能に慣れる必要があり、実際には非常に簡単ですapply,withおよびlet。何が起こる

fun idiomatic(myInt: Int) = (myInt % 2 == 0).apply { 
    if (this) println("is equal") else println("in not equal") 
} 

:適用は直接受信機は、thisと呼ばれる機能となり、この場合、中Anyオブジェクト、Boolean(条件)に呼び出されます。この場合、applyは何が必要です。重要なのは、applyは、提供されたコードブロックが実行された後、その受信機を返します。これはあなたのBooleanです。

私はこれがあなたが必要としていることを望みます!

関連する問題