Skip to content

6. Interfejsy funkcjonalne biblioteki RxJava

Klasa Observable stanowi podstawę biblioteki asynchronicznej RxJava. Wykazuje ona wiele podobieństw do klasy Stream, którą właśnie przedstawiliśmy. Podobnie jak ona, posiada bardzo wiele metod – kilkadziesiąt. Podobnie jak ta, metody te przyjmują jako parametry instancje interfejsów funkcjonalnych. Zaczniemy od przedstawienia najczęściej spotykanych z nich: [Actioni] i [Funci].

6.1. Przykład-01: interfejs funkcjonalny [Action0]

  

Interfejs [Action0] wygląda następująco:

  • Interfejs [Action0] posiada jedyną metodę o sygnaturze [2]: void call(). Wywodzi się on z interfejsów [Action] i [1, 3]. Interfejs [Action] nie posiada żadnych metod. Tego typu interfejsy nazywane są interfejsami znacznikowymi [4]. Służą one głównie do pisania: if(c instanceOf(Action)) {...}. Interfejs [Action] sam wywodzi się z interfejsu znacznikowego [Function] [4-6];
 

Interfejs [Action0] zilustrujemy za pomocą poniższego kodu (Przykład01):


package dvp.rxjava.lamdbas;

import rx.functions.Action0;

public class Exemple01 {
  public static void main(String[] args) {
    // Akcja 0
    Action0 a01 = new Action0() {
      @Override
      public void call() {
        System.out.println("anonymous a01.call");
      }
    };
    Action0 a02 = () -> System.out.println("lambda ao2.call");
    // wyświetlenia
    a01.call();
    a02.call();
  }
}
  • wiersze 8–13: implementacja interfejsu [Action0] za pomocą klasy anonimowej;
  • wiersze 8–13: implementacja interfejsu [Action0] za pomocą wyrażenia lambda;

Wyniki są następujące:

anonymous a01.call
lambda ao2.call

6.2. Przykład-02, 03: interfejs funkcjonalny [Actioni]

  

Interfejs [Action1] wygląda następująco:

 

Zilustrujemy to poniższym kodem (Przykład 02):


package dvp.rxjava.lamdbas;

import rx.functions.Action1;

public class Exemple02 {
  public static void main(String[] args) {
    // Akcja1
    Action1<Integer> a10 = new Action1<Integer>() {
      @Override
      public void call(Integer integer) {
        System.out.printf("anonymous a10.call (%s)%n", integer);
      }
    };
    Action1<Double> a11 = (d -> System.out.printf("lambda a11.call (%s)%n", d));

    // uruchomienia
    a10.call(20);
    a11.call(17.4);
  }
}

co daje następujący wynik:

anonymous a10.call (20)
lambda a11.call (17.4)

Ogólnie rzecz biorąc, [Actioni] (0<=i<=9) jest interfejsem funkcjonalnym posiadającym jedyną metodę o sygnaturze: void call(T1 t1, T2 t2, ..., Ti ti). Oto przykład dla [Action2] (Przykład03):


package dvp.rxjava.lamdbas;

import rx.functions.Action2;

public class Exemple03 {
  public static void main(String[] args) {
    // Akcja 2
    Action2<Integer, Double> a20 = new Action2<Integer, Double>() {
      @Override
      public void call(Integer integer, Double aDouble) {
        System.out.printf("anonymous a20.call(%s,%s)%n", integer, aDouble);
      }
    };
    Action2<Integer, Double> a21 = (i, d) -> System.out.printf("lambda a21.call(%s,%s)%n", i, d);
    // wykonania
    a20.call(10,11.3);
    a21.call(5,5.6);
  }
}

Otrzymany wynik jest następujący:

anonymous a20.call(10,11.3)
lambda a21.call(5,5.6)

6.3. Przykłady 04, 05: interfejs funkcjonalny [Funci]

  

Interfejs [Func0] wygląda następująco:

 

Tym razem metoda [call] tego interfejsu zwraca wynik typu R.

Zilustrujemy ten interfejs za pomocą następującego kodu:


package dvp.rxjava.lamdbas;

import rx.functions.Func0;

public class Exemple04 {
  public static void main(String[] args) {
    // Funkcja0
    Func0<String> f00 = new Func0<String>() {
      @Override
      public String call() {
        return "anonymous f00.call";
      }
    };
    Func0<String> f01 = () -> "lambda f01.call";
    // wykonania
    System.out.println(f00.call());
    System.out.println(f01.call());
  }
}

co daje następujące wyniki:

anonymous a20.call(10,11.3)
lambda a21.call(5,5.6)

Ogólnie rzecz biorąc, [Funci] (0<=i<=9) jest interfejsem funkcjonalnym posiadającym jedyną metodę o sygnaturze: R call(T1 t1, T2 t2, ..., Ti ti). Oto przykład dla [Func2] (Przykład05):


package dvp.rxjava.lamdbas;

import rx.functions.Func2;

public class Exemple05 {
  public static void main(String[] args) {
    // Func2
    Func2<Integer, Double, String> f20 = new Func2<Integer, Double, String>() {
      @Override
      public String call(Integer integer, Double aDouble) {
        return String.format("anonymous f20.call(%s,%s)", integer, aDouble);
      }
    };
    Func2<Integer, Double, String> f21 = (i,d) -> String.format("anonymous f21.call(%s,%s)", i, d);
    // wyświetlenia
    System.out.println(f20.call(10,10.2));
    System.out.println(f21.call(100, 100.3));
  }
}

co daje następujące wyniki:

anonymous f20.call(10,10.2)
anonymous f21.call(100,100.3)