正确地将RxJava代码转换为Kotlin

时间:2017-10-10 19:55:15

标签: java android kotlin rx-java rx-java2

我正在学习Kotlin和RxJava。我在Java中使用这样的代码:

public class MainActivity extends AppCompatActivity {

private HashMap<String, Object> cacheToInsertToDb;


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    cacheToInsertToDb = new HashMap<>();

    Observable.interval(1, TimeUnit.SECONDS)
            .take(30) // up to 30 items
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new Consumer<Long>() {
                @Override
                public void accept(Long aLong) throws Exception {
                    cacheToInsertToDb.put(aLong+"", aLong);
                    Log.d("Observable", cacheToInsertToDb.values().toString());
                }
            }, new Consumer<Throwable>() {
                @Override
                public void accept(Throwable throwable) throws Exception {

                }
            }, new Action() {
                @Override
                public void run() throws Exception {

                }
            });

    Observable.interval(10, TimeUnit.SECONDS)
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new Consumer<Long>() {
                @Override
                public void accept(Long aLong) throws Exception {
                    proceedVlues(cacheToInsertToDb.values());
                    cacheToInsertToDb.clear();
                    Log.d("CLEARED", cacheToInsertToDb.values().toString());
                }
            }, new Consumer<Throwable>() {
                @Override
                public void accept(Throwable throwable) throws Exception {

                }
            }, new Action() {
                @Override
                public void run() throws Exception {

                }
            });

}

private void proceedVlues(Collection<Object> values) {
        for(Object v: values){
            if(v instanceof Long){
                Log.d("proceedVlues", v+"");
            }
        }
   }
}

但是,当我在AndroidStudio中进行转换时,IDE中会出现大量错误。

这是Kotlin中的代码,在Android Studio中转换:

class MainActivity : AppCompatActivity() {

private var cacheToInsertToDb: HashMap<String, Any>? = null


override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    cacheToInsertToDb = HashMap()

    Observable.interval(1, TimeUnit.SECONDS)
            .take(30) // up to 30 items
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(object : Consumer<Long> {
                @Throws(Exception::class)
                override fun accept(aLong: Long?) {
                    cacheToInsertToDb!!.put(aLong!!.toString() + "", aLong)
                    Log.d("Observable", cacheToInsertToDb!!.values.toString())
                }
            }, Consumer { }, Action { })

    Observable.interval(10, TimeUnit.SECONDS)
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(object : Consumer<Long> {
                @Throws(Exception::class)
                override fun accept(aLong: Long?) {
                    proceedVlues(cacheToInsertToDb!!.values)
                    cacheToInsertToDb!!.clear()
                    Log.d("CLEARED", cacheToInsertToDb!!.values.toString())
                }
            }, Consumer { }, Action { })

}

private fun proceedVlues(values: Collection<Any>) {
    for (v in values) {
        if (v is Long) {
            Log.d("proceedVlues", v.toString() + "")
        }
      }
   }
}

它给了我错误的下划线&#34;未解析的@ Throws&#34;和&#34;接受&#39;覆盖nothig&#34;。如何将Java代码正确转换为Kotlin?

2 个答案:

答案 0 :(得分:1)

您可以使用安全的npe和lambdas更新代码。有时,从java转换为kotlin的代码需要一些外观。

  .subscribe(object : Consumer<Long> {
                    @Throws(Exception::class)
                    override fun accept(aLong: Long?) {
                        cacheToInsertToDb!!.put(aLong!!.toString() + "", aLong)
                        Log.d("Observable", cacheToInsertToDb!!.values.toString())
                    }
                }, Consumer { }, Action { })

.subscribe(Consumer<Long?>{ aLong ->
                    cacheToInsertToDb?.put(aLong?.toString() ?: "", aLong)
                    Log.d("Observable", cacheToInsertToDb?.values.toString())

            }, Consumer { }, Action { })

答案 1 :(得分:1)

在kotlin中,你可以用lambda表达式(doc)替换只有一个方法的接口实现。

  

就像Java 8一样,Kotlin支持SAM转换。这意味着只要接口方法的参数类型与Kotlin函数的参数类型匹配,Kotlin函数文字就可以使用单个非默认方法自动转换为Java接口的实现。

这会给你:

.subscribe(
        { item: Long? ->

        },
        { t: Throwable ->

        },
        {//onComplete

        })

另外,取决于您使用的是RxJava2(doc):

  

RxJava 2.x不再接受空值,以下内容将产生   NullPointerException立即或作为信号

因此您确定在onNext中未收到空值,并且您可以删除安全无效检查?

.subscribe(
        { item: Long ->

        },
        { t: Throwable ->

        },
        {//onComplete

        })