Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Intro to Functional Reactive Programming (Droidcon MTL 2015)

Juan Gomez
April 12, 2015

Intro to Functional Reactive Programming (Droidcon MTL 2015)

This talk will be an introduction to the ideas behind functional reactive programming and how you can move away from traditional synchronous state management with variables to asynchronous streams of data instead. You will learn how Rx (Reactive Extensions) Observables simplify concurrent code and let you write asynchronous, message based Android apps, in ways that are more elegant and a bit less error prone than traditional Android mechanisms.

We will also take a look at some Higher-order functions such as map(), flatmap(), filter() and reduce() that enable you to write simple, expressive and concise code to process Observables and solve problems in many common Android scenarios. These powerful yet easy to use abstractions will let you write asynchronous code in a more straightforward, declarative fashion; making your life as an Android developer a lot easier.

Juan Gomez

April 12, 2015
Tweet

More Decks by Juan Gomez

Other Decks in Technology

Transcript

  1. Functional Reactive
    Programming
    Juan Gomez

    View full-size slide

  2. Intro
    Who am I?
    • Mobile Engineer at Netflix
    • Previously at Eventbrite and OneLouder Apps
    • Android & Python Developer

    View full-size slide

  3. Agenda
    • Brief introduction to Rx and why we want to use it.
    • Observables and useful operators to transform
    Observables.
    • Brief introduction to RxAndroid.

    View full-size slide

  4. Multithreading is hard!
    This is a lesson I seem to learn every few years:
    multithreading is hard.

    Once you think you now understand it and are an
    expert, you are heading soon to another painful
    lesson that multithreading is hard.
    - Dianne Hackborn
    April 2012

    View full-size slide

  5. What Is Functional Reactive
    Programming?
    • A style of programming
    based on two key ideas:
    continuous time-varying
    behaviors, and event-based
    reactivity.
    • Popularized by Erik Meijer
    when he created the Rx
    library for .NET while at
    Microsoft.

    View full-size slide

  6. Functional Reactive
    Programming in Java
    aObservable.map(x -> x*x) //Square
    .reduce((a, b) -> a+b) //Sum
    .subscribe(x -> println(x)); //Show

    View full-size slide

  7. Why Functional Reactive
    Programming
    • Writing concurrent programs correctly is difficult.
    • You can transform & compose asynchronous
    operations.
    • High-level abstractions
    • Standard error handling

    View full-size slide

  8. Rx Family
    • C#: Rx.NET
    • JavaScript: RxJS
    • RxJava (Java, Scala, Groovy, Clojure, Kotlin)
    • Ruby: Rx.rb
    • Python: RxPY
    • More at: http://reactivex.io/

    View full-size slide

  9. RxJava
    • It’s a JVM implementation of Reactive Extensions
    • Extends Observer pattern to support data/event
    and compose operators in abstract.
    • Started at Netflix
    • Supports Java 6+ & Android 2.3+
    • Java 8 lambda support

    View full-size slide

  10. Observables
    event Iterable (pull) Observable (push)
    retrieve data T next() onNext(T)
    discover error throws Exception onError(Exception)
    complete !hasNext() onCompleted()
    It’s like the GoF Observer++

    View full-size slide

  11. Push vs Pull

    View full-size slide

  12. Observer Pattern on Android

    View full-size slide

  13. Android using RFP

    View full-size slide

  14. RxJava on Java 7
    aObservable.filter(new Func1() {
    public Boolean call(Integer n) {
    return n % 2 == 0;
    }
    })
    .map(new Func1() {
    public Integer call(Integer n) {
    return n * n;
    }
    })
    .subscribe(new Action1() {
    public void call(Integer n) {
    System.out.println(n);
    }
    });

    View full-size slide

  15. Retrolambda
    Retrolambda lets you take advantage of Java 8
    features like lambda expressions and method
    references on Java 7 or lower.
    • Retrolambda
    • https://github.com/orfjackal/retrolambda
    • Gradle plugin
    • https://github.com/evant/gradle-retrolambda

    View full-size slide

  16. RxJava using Retrolambda
    aObservable.filter(n -> n % 2 == 0)
    .map(n -> n * n)
    .subscribe(System.out::println);

    View full-size slide

  17. Creating an Observable

    View full-size slide

  18. Creating an Observable
    List aList = ...;
    ob = Observable.create(subscriber -> {
    try {
    for (String s : aList) {
    if (subscriber.isUnsubscribed())
    return;
    subscriber.onNext(s);
    }
    subscriber.onCompleted();
    } catch (Exception e) {
    subscriber.onError(e);
    }
    });

    View full-size slide

  19. Creating an Observable
    List aList = ...;
    Observable ob = Observable.from(aList);

    View full-size slide

  20. Creating an Observable
    Observable> ob = Observable.just(aList);
    Observable ob2 = Observable.just("Some String");

    View full-size slide

  21. Creating an Observable
    • repeat( )
    • range( )
    • interval( )
    • timer( )
    • empty( )
    • error( )
    • More at: https://github.com/ReactiveX/RxJava/wiki/Creating-
    Observables

    View full-size slide

  22. Transforming Observables

    View full-size slide

  23. Transforming Observables
    Observable.range(0, 5)
    .map(x -> toBinaryString(x*x))
    .subscribe(s -> println(s),
    err -> err.printStackTrace(),
    () -> println("done"));
    0
    1
    100
    1001
    10000
    done

    View full-size slide

  24. Transforming Observables

    View full-size slide

  25. Transforming Observables
    1
    2
    2
    3
    3
    3
    Observable.range(1, 3)
    .flatMap(x -> Observable.just(x).repeat(x))
    .subscribe(System.out::println);

    View full-size slide

  26. Filtering Observables

    View full-size slide

  27. Filtering Observables
    0
    2
    4
    6
    8
    Observable.range(0, 10)
    .filter(x -> (x % 2) == 0)
    .subscribe(System.out::println);

    View full-size slide

  28. Filtering Observables
    • distinct( )
    • first( )
    • take( )
    • skip( )
    • elementAt( )
    • sample( )
    • more...
    • More at: https://github.com/ReactiveX/RxJava/wiki/Filtering-Observables

    View full-size slide

  29. Aggregate Operators

    View full-size slide

  30. Aggregate Operators
    3628800
    Observable.range(1, 10)
    .reduce((a, b) -> a*b)
    .subscribe(System.out::println);

    View full-size slide

  31. Combining Observables

    View full-size slide

  32. Combining Observables
    a_A
    b_B
    c_C
    Observable lower =
    Observable.from(new String[]{"a", "b", "c"});
    Observable upper =
    Observable.from(new String[]{"A", "B", "C"});
    Observable.zip(lower, upper, Pair::create)
    .map(pair -> pair.first +"_" +pair.second)
    .subscribe(System.out::println);

    View full-size slide

  33. Threading
    • observeOn
    • specify on which Scheduler a Subscriber should
    observe the Observable
    • subscribeOn
    • specify which Scheduler an Observable should use
    when its subscription is invoked
    • https://github.com/ReactiveX/RxJava/wiki/
    Scheduler

    View full-size slide

  34. Backpressure
    • Backpressure is the situation in which an
    Observable is emitting items more rapidly than an
    operator or subscriber can consume them.
    • RxJava offers a variety of strategies like throttling
    with which you can exercise flow control in order to
    alleviate the problems caused by backpressure.
    • https://github.com/ReactiveX/RxJava/wiki/Backpressure

    View full-size slide

  35. Hot and Cold Observables
    • A “cold” Observable waits to start emitting items
    until an observer subscribes, and so an observer
    can “observe” the whole sequence.
    • A “hot” Observable may begins emitting items as
    soon as it is created.

    View full-size slide

  36. RxAndroid
    • Android specific bindings for RxJava.
    • https://github.com/ReactiveX/RxAndroid
    • Scheduler on main UI thread or a given Android Handler thread.
    • AndroidSchedulers
    • HandlerThreadScheduler
    • Reactive components for common Android use cases and UI widgets
    • AndroidObservable
    • ViewObservable

    View full-size slide

  37. Android Example
    /* API */
    Observable getFromServer(String key);
    Observable getFromDB(String key);
    /* Code */
    ViewObservable.clicks(btnClick)
    .map(x -> "myid")
    .observeOn(Schedulers.io())
    .flatMap(this::getFromDB)
    .flatMap(this::getFromServer)
    .observeOn(AndroidSchedulers.mainThread())
    .subscribe(x -> Toast.makeText(context, x,
    LENGTH_LONG).show());

    View full-size slide

  38. Summary
    • Embrace Reactive and Functional Thinking
    • Manipulating Streams of Data simplifies who
    we think (and build) our programs.
    • RxJava is a powerful tool to improve your
    Android Code

    View full-size slide

  39. Useful links
    • https://github.com/ReactiveX/RxJava/wiki/
    • https://github.com/ReactiveX/RxAndroid
    • http://reactivex.io/documentation/operators.html
    • http://blog.danlew.net/2014/09/15/grokking-rxjava-part-1/
    • https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

    View full-size slide

  40. Thank You!
    Twitter: @_juandg
    Email: jgomez@netflix.com
    Lanyrd: lanyrd.com/profile/juandg/

    View full-size slide