RxJava - Quick Guide



RxJava - Overview

RxJava is a Java based extension of ReactiveX. It provides implementation or ReactiveX project in Java. Following are the key characteristics of RxJava.

  • Extends the observer pattern.

  • Support sequences of data/events.

  • Provides operators to compose sequences together declaratively.

  • Handles threading, synchronization, thread-safety and concurrent data structures internally.

What is ReactiveX?

ReactiveX is a project which aims to provide reactive programming concept to various programming languages. Reactive Programming refers to the scenario where program reacts as and when data appears. It is a event based programming concept and events can propagate to registers observers.

As per the Reactive, they have combined the best of Observer pattern, Iterator pattern and functional pattern.

The Observer pattern done right. ReactiveX is a combination of the best ideas from the Observer pattern, the Iterator pattern, and functional programming.

Functional Programming

Functional programming revolves around building the software using pure functions. A pure function do not depends upon previous state and always returns the same result for the same parameters passed. Pure functions helps avoiding problems associated with shared objects, mutable data and side effects often prevalent in multi-threading environments.

Reactive Programming

Reactive programming refers to event driven programming where data streams comes in asynchronous fashion and get processed when they are arrived.

Functional Reactive Programming

RxJava implements both the concepts together, where data of streams changes over time and consumer function reacts accordingly.

The Reactive Manifesto

Reactive Manifesto is an on-line document stating the high standard of application software systems. As per the manifesto, following are the key attributes of a reactive software −

  • Responsive − Should always respond in a timely fashion.

  • Message Driven − Should use asynchronous message-passing between components so that they maintain loose coupling.

  • Elastic − Should stay responsive even under high load.

  • Resilient − Should stay responsive even if any component(s) fail.

Key components of RxJava

RxJava have two key components: Observables and Observer.

  • Observable − It represents an object similar to Stream which can emit zero or more data, can send error message, whose speed can be controlled while emitting a set of data, can send finite as well as infinite data.

  • Observer − It subscribes to Observable's data of sequence and reacts per item of the observables. Observers are notified whenever Observable emits a data. An Observer handles data one by one.

An observer is never notified if items are not present or a callback is not returned for a previous item.

RxJava - Environment Setup

This chapter will guide you on how to prepare a development environment to start your work with RxJava. It will also teach you how to set up JDK on your machine before you set up RxJava −

Setup Java Development Kit (JDK)

You can download the latest version of SDK from Oracle's Java site − Java SE Downloads. You will find instructions for installing JDK in downloaded files, follow the given instructions to install and configure the setup. Finally set PATH and JAVA_HOME environment variables to refer to the directory that contains java and javac, typically java_install_dir/bin and java_install_dir respectively.

If you are running Windows and have installed the JDK in C:\jdk-24, you would have to put the following line in your C:\autoexec.bat file.

set PATH=C:\jdk-24;%PATH% 
set JAVA_HOME=C:\jdk-24

Alternatively, on Windows NT/2000/XP, you will have to right-click on My Computer, select Properties → Advanced → Environment Variables. Then, you will have to update the PATH value and click the OK button.

On Unix (Solaris, Linux, etc.), if the SDK is installed in /usr/local/jdk-24 and you use the C shell, you will have to put the following into your .cshrc file.

setenv PATH /usr/local/jdk-24/bin:$PATH 
setenv JAVA_HOME /usr/local/jdk-24

Alternatively, if you use an Integrated Development Environment (IDE) like Borland JBuilder, Eclipse, IntelliJ IDEA, or Sun ONE Studio, you will have to compile and run a simple program to confirm that the IDE knows where you have installed Java. Otherwise, you will have to carry out a proper setup as given in the document of the IDE.

Popular Java Editors

To write your Java programs, you need a text editor. There are many sophisticated IDEs available in the market. But for now, you can consider one of the following −

  • Notepad − On Windows machine, you can use any simple text editor like Notepad (Recommended for this tutorial), TextPad.

  • Netbeans − It is a Java IDE that is open-source and free, which can be downloaded from www.netbeans.org/index.html.

  • Eclipse − It is also a Java IDE developed by the eclipse open-source community and can be downloaded from www.eclipse.org.

Download RxJava Archive

Download the latest version of RxJava jar files. At the time of writing this tutorial, we have downloaded rxjava-3.1.11.jar and reactive-streams-1.0.4.jar, and copied it into C:\>RxJava folder.

OS Archive name
Windows rxjava-3.1.11.jar;reactive-streams-1.0.4.jar
Linux rxjava-3.1.11.jar;reactive-streams-1.0.4.jar
Mac rxjava-3.1.11.jar;reactive-streams-1.0.4.jar

Set RxJava Environment

Set the RxJava environment variable to point to the base directory location where rxjava jar is stored on your machine. Let's assuming we've stored rxjava-3.1.11.jar in the RxJava folder.

Sr.No OS & Description
1

Windows

Set the environment variable RxJava to C:\RxJava

2

Linux

export RxJava = /usr/local/RxJava

3

Mac

export RxJava = /Library/RxJava

Set CLASSPATH Variable

Set the CLASSPATH environment variable to point to the rxjava jar location.

Sr.No OS & Description
1

Windows

Set the environment variable CLASSPATH to %CLASSPATH%;%RxJava%\rxjava-3.1.11.jar:%RxJava%\reactive-streams-1.0.4.jar;.;

2

Linux

export CLASSPATH = $CLASSPATH:$RxJava/rxjava-3.1.11.jar:$RxJava/reactive-streams-1.0.4.jar:.

3

Mac

export CLASSPATH = $CLASSPATH:$RxJava/rxjava-3.1.11.jar:$RxJava/reactive-streams-1.0.4.jar:.

RxJava - How Observable works

Observables represents the sources of data where as Observers (Subscribers) listen to them. In nutshell, an Observable emits items and a Subscriber then consumes these items.

Observable

  • Observable provides data once subscriber starts listening.

  • Observable can emit any number of items.

  • Observable can emit only signal of completion as well with no item.

  • Observable can terminate successfully.

  • Observable may never terminate. e.g. a button can be clicked any number of times.

  • Observable may throw error at any point of time.

Subscriber

  • Observable can have multiple subscribers.

  • When an Observable emits an item, each subscriber onNext() method gets invoked.

  • When an Observable finished emitting items, each subscriber onComplete() method gets invoked.

  • If an Observable emits error, each subscriber onError() method gets invoked.

RxJava - Creating Observables

Base Classes

Following are the base classes to create observables.

  • Flowable − 0..N flows, Emits 0 or n items. Supports Reactive-Streams and back-pressure.

  • Observable − 0..N flows ,but no back-pressure.

  • Single − 1 item or error. Can be treated as a reactive version of method call.

  • Completable − No item emitted. Used as a signal for completion or error. Can be treated as a reactive version of Runnable.

  • MayBe − Either No item or 1 item emitted. Can be treated as a reactive version of Optional.

Methods

Following are the convenient methods to create observables in Observable class.

  • just(T item) − Returns an Observable that signals the given (constant reference) item and then completes.

  • fromIterable(Iterable source) − Converts an Iterable sequence into an ObservableSource that emits the items in the sequence.

  • fromArray(T... items) − Converts an Array into an ObservableSource that emits the items in the Array.

  • fromCallable(Callable supplier) − Returns an Observable that, when an observer subscribes to it, invokes a function you specify and then emits the value returned from that function.

  • fromFuture(Future future) − Converts a Future into an ObservableSource.

  • interval(long initialDelay, long period, TimeUnit unit) − Returns an Observable that emits a 0L after the initialDelay and ever increasing numbers after each period of time thereafter.

RxJava - Using Flowable

The Flowable class represents 0..N flows, Emits 0 or n items. Supports Reactive-Streams and back-pressure.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.core.Flowable<T> class −

public abstract class Flowable<T>
   extends Object
      implements Publisher<T>

Protocol

Following is the sequential protocol that Flowable Observable operates −

onSubscribe onNext* (onError | OnComplete)?

Example - Creating a Flowable Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Flowable;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      Flowable.just("Hello world").subscribe(System.out::println);
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of Flowable Observable Class to get Data after a delay of 2 seconds

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Flowable;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableSingleObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;
import io.reactivex.rxjava3.subscribers.DisposableSubscriber;

public class ObservableTester  {
   public static void main(String[] args)  throws InterruptedException {
      //Create the observable
      Flowable<String> testFlowable = Flowable.just("Hello World");

      //Create an observer
      Disposable disposable = testFlowable
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(
            new DisposableSubscriber<String>() {
               @Override 
               public void onStart() {
                  System.out.println("Start!");
                  request(1);
               }
               @Override 
               public void onNext(String t) {
                  System.out.println(t);
                  request(1);
               }
               @Override
               public void onError(Throwable t) {
                  t.printStackTrace();
               }
               @Override 
               public void onComplete() {
                  System.out.println("Done!");
               }
            }); 
      Thread.sleep(3000);
      //start observing
      disposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Start!
Hello World
Done!

RxJava - Single Observable

The Single class represents the single value response. Single observable can only emit either a single successful value or an error. It does not emit onComplete event.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.core.Single<T> class −

public abstract class Single<T>
   extends Object
      implements SingleSource<T>

Protocol

Following is the sequential protocol that Single Observable operates −

onSubscribe (onSuccess | onError)?

Example - Creating a Single Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Single;

public class ObservableTester  {
   public static void main(String[] args)  throws InterruptedException {
      Single.just("Hello world").subscribe(System.out::println);
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of Single Observable Class to get Data after a delay of 2 seconds

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Single;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableSingleObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args)  throws InterruptedException {
      //Create the observable
      Single<String> testSingle = Single.just("Hello World");

      //Create an observer
      Disposable disposable = testSingle
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(
         new DisposableSingleObserver<String>() {

         @Override
         public void onError(Throwable e) { 
            e.printStackTrace();
         }

         @Override
         public void onSuccess(String value) {
            System.out.println(value);
         }
      }); 
      Thread.sleep(3000);
      //start observing
      disposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

RxJava - Maybe Observable

The Maybe class represents deferred response. Maybe observable can emit either a single successful value or no value.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.core.Maybe<T> class −

public abstract class Maybe<T>
   extends Object
      implements MaybeSource<T>

Protocol

Following is the sequential protocol that Single Observable operates −

onSubscribe (onSuccess | onError | OnComplete)?

Example - Creating a MayBe Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Maybe;

public class ObservableTester  {
   public static void main(String[] args)  throws InterruptedException {
      Maybe.just("Hello world").subscribe(System.out::println);
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of Maybe Observable Class to get Data after a delay of 2 seconds

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Maybe;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableMaybeObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args)  throws InterruptedException {
      //Create the observable
      Maybe<String> testMaybe = Maybe.just("Hello World");

      //Create an observer
      Disposable disposable = testMaybe
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(
         new DisposableMaybeObserver<String>() {

         @Override
         public void onError(Throwable e) { 
            e.printStackTrace();
         }

         @Override
         public void onSuccess(String value) {
            System.out.println(value);
         }
         @Override
         public void onComplete() {
            System.out.println("Done!");
         }
      }); 
      Thread.sleep(3000);
      //start observing
      disposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

RxJava - Completable Observable

The Completable class represents deferred response. Completable observable can either indicate a successful completion or error.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.core.Completable<T> class −

public abstract class Completable
   extends Object
      implements CompletableSource

Protocol

Following is the sequential protocol that Single Observable operates −

onSubscribe (onError | OnComplete)?

Example - Creating a Completable Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Completable;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      Completable.complete().doOnComplete(() -> System.out.println("Hello World")).subscribe();
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of Completable Observable Class to get Data after a delay of 2 seconds

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Completable;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableCompletableObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;


public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {

      //Create an observer
      Disposable disposable = Completable.complete()
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(new DisposableCompletableObserver() {
         @Override
         public void onError(Throwable e) { 
            e.printStackTrace();
         }
         @Override
         public void onStart() {
            System.out.println("Started!");
         }
         @Override
         public void onComplete() {
            System.out.println("Done!");
         }
      }); 
      Thread.sleep(3000);
      //start observing
      disposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Started!
Done!

RxJava - CompositeDisposable Observable

The CompositeDisposable lass represents a container which can hold multiple disposable and offers O(1) complexity of adding and removing disposables.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.disposables.CompositeDisposable class −

public final class CompositeDisposable
   extends Object
      implements Disposable, DisposableContainer

Example - Creating a CompositeDisposable Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Single;
import io.reactivex.rxjava3.disposables.CompositeDisposable;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      CompositeDisposable compositeDisposable = new CompositeDisposable(
         Single.just("Hello world").subscribe(System.out::println)
      );
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of CompositeDisposable Observable Class to get Data using multiple disposable

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Maybe;
import io.reactivex.rxjava3.core.Single;
import io.reactivex.rxjava3.disposables.CompositeDisposable;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableMaybeObserver;
import io.reactivex.rxjava3.observers.DisposableSingleObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      CompositeDisposable compositeDisposable = new CompositeDisposable();

      //Create an Single observer 
      Disposable disposableSingle = Single.just("Hello World")
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(
            new DisposableSingleObserver<String>() {
               @Override
               public void onError(Throwable e) {
                  e.printStackTrace();
               }

               @Override
               public void onSuccess(String value) {
                  System.out.println(value);
               }
            }); 

      //Create an observer
      Disposable disposableMayBe = Maybe.just("Hi")
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(new DisposableMaybeObserver<String>() {
            @Override
            public void onError(Throwable e) { 
               e.printStackTrace();
            }

            @Override
            public void onSuccess(String value) {
               System.out.println(value);
            }

            @Override
            public void onComplete() {
               System.out.println("Done!");
            }
         }); 

      Thread.sleep(3000);

      compositeDisposable.add(disposableSingle);
      compositeDisposable.add(disposableMayBe);

      //start observing
      compositeDisposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Hello World
Hi

RxJava - Creating Operators



Following are the operators which are used to create an Observable.

Sr.No. Operator & Description
1

create

Creates an Observable from scratch and allows observer method to call programmatically.

2

defer

Do not create an Observable until an observer subscribes. Creates a fresh observable for each observer.

3

empty/never/throw

Creates an Observable with limited behavior.

4

from

Converts an object/data structure into an Observable.

5

interval

Creates an Observable emitting integers in sequence with a gap of specified time interval.

6

just

Converts an object/data structure into an Observable to emit the same or same type of objects.

7

range

Creates an Observable emitting integers in sequence of given range.

8

repeat

Creates an Observable emitting integers in sequence repeatedly.

9

start

Creates an Observable to emit the return value of a function.

10

timer

Creates an Observable to emit a single item after given delay.

11

fromArray

Converts an array into an Observable.

Example - Creating Observable using Array of Items

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using fromArray operator to create an Observable
public class ObservableTester  {
   public static void main(String[] args) { 
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable = Observable.fromArray(letters);
      observable
         .map(String::toUpperCase)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

ABCDEFG

Example - Creating Observable using a Single Item

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using just operator to create an Observable
public class ObservableTester  {
   public static void main(String[] args) { 
      String message = "Hello World";
      Observable<String> observable = Observable.just(message);
      observable
         .map(String::toUpperCase)
         .subscribe( System.out::println);
   }
}

Output

Compile and Run the code to verify the following output −

HELLO WORLD

RxJava - Transforming Operators

Following are the operators which are used to transform an item emitted from an Observable.

Sr.No. Operator & Description
1

buffer

Gathers items from Observable into bundles periodically and then emit the bundles rather than items.

2

flatMap

Used in nested observables. Transforms items into Observables. Then flatten the items into single Observable.

3

groupBy

Divide an Observable into set of Observables organized by key to emit different group of items.

4

map

Apply a function to each emitted item to transform it.

5

scan

Apply a function to each emitted item, sequentially and then emit the successive value.

6

window

Gathers items from Observable into Observable windows periodically and then emit the windows rather than items.

Example - Transforming Letters to Upper case using map Operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using map operator to tranform an item emitted
public class ObservableTester  {
   public static void main(String[] args) { 
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable = Observable.fromArray(letters);
      observable
         .map(String::toUpperCase)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

ABCDEFG

Example - Flatten internal observables using flatmap Operator

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.schedulers.Schedulers;

//Using flatmap operator to flatten observables
public class ObservableTester  {
   public static void main(String[] args) throws InterruptedException { 
      Observable<String> userIds = Observable.just("user1", "user2", "user3");

      userIds.flatMap(userId -> getUserDetails(userId))
         .subscribe(userDetails -> System.out.println("Received: " + userDetails));

      // Keep the main thread alive to see the asynchronous results
      Thread.sleep(1000);
   }

   // Simulate an asynchronous network call to get user details
   public static Observable<String> getUserDetails(String userId) {
      return Observable.just("User Details of " + userId)
         .delay(100, TimeUnit.MILLISECONDS) 
         .subscribeOn(Schedulers.io());
   }
}

Output

Compile and Run the code to verify the following output −

Received: User Details of user3
Received: User Details of user1
Received: User Details of user2

RxJava - Filtering Operators

Following are the operators which are used to selectively emit item(s) from an Observable.

Sr.No. Operator & Description
1

debounce

Emits items only when timeout occurs without emiting another item.

2

distinct

Emits only unique items.

3

elementAt

emit only item at n index emitted by an Observable.

4

filter

Emits only those items which pass the given predicate function.

5

first

Emits the first item or first item which passed the given criteria.

6

ignoreElements

Do not emits any items from Observable but marks completion.

7

last

Emits the last element from Observable.

8

sample

Emits the most recent item with given time interval.

9

skip

Skips the first n items from an Observable.

10

skipLast

Skips the last n items from an Observable.

11

take

takes the first n items from an Observable.

12

takeLast

takes the last n items from an Observable.

Example - Taking First two items

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

// Using take operator to filter items
public class ObservableTester  {
   public static void main(String[] args) { 
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable = Observable.fromArray(letters);
      observable
         .take(2)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

ab

Example - Skipping First two items

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using map operator to tranform an item emitted
public class ObservableTester  {
   public static void main(String[] args) { 
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable = Observable.fromArray(letters);
      observable
         .skip(2)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

cdefg

RxJava - Combining Operators

Following are the operators which are used to create a single Observable from multiple Observables.

Sr.No. Operator & Description
1 and/then/when

Combine item sets using Pattern and Plan intermediaries.

2 combineLatest

Combine the latest item emitted by each Observable via a specified function and emit resulted item.

3 join

Combine items emitted by two Observables if emitted during time-frame of second Observable emitted item.

4 merge

Combines the items emitted of Observables.

5 startWith

Emit a specified sequence of items before starting to emit the items from the source Observable

6 switch

Emits the most recent items emitted by Observables.

7 zip

Combines items of Observables based on function and emits the resulted items.

Example - Using combineLatest Operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using combineLatest operator to combine Observables
public class ObservableTester {
   public static void main(String[] args) {    
      Integer[] numbers = { 1, 2, 3, 4, 5, 6};
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable1 = Observable.fromArray(letters);
      Observable<Integer> observable2 = Observable.fromArray(numbers);
      Observable.combineLatest(observable1, observable2, (a,b) -> a + b)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

g1g2g3g4g5g6

Example - Using concat Operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using concat operator to combine Observables
public class ObservableTester {
   public static void main(String[] args) {    
      Integer[] numbers = { 1, 2, 3, 4, 5, 6};
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable1 = Observable.fromArray(letters);
      Observable<Integer> observable2 = Observable.fromArray(numbers);
      Observable.concat(observable1, observable2)
         .subscribe( letter -> result.append(letter));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

abcdefg123456

RxJava - Utility Operators

Following are the operators which are often useful with Observables.

Sr.No. Operator & Description
1

delay

Register action to handle Observable life-cycle events.

2

materialize/dematerialize

Represents item emitted and notification sent.

3

observeOn

Specify the scheduler to be observed.

4

serialize

Force Observable to make serialized calls.

5

subscribe

Operate upon the emissions of items and notifications like complete from an Observable

6

subscribeOn

Specify the scheduler to be used by an Observable when it is subscribed to.

7

timeInterval

Convert an Observable to emit indications of the amount of time elapsed between emissions.

8

timeout

Issues error notification if specified time occurs without emitting any item.

9

timestamp

Attach timestamp to each item emitted.

9

using

Creates a disposable resource or same lifespan as that of Observable.

Example - Usage of subscribe operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using subscribe operator to subscribe to an Observable
public class ObservableTester {
   public static void main(String[] args) {    
	   String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
       final StringBuilder result = new StringBuilder();
       Observable<String> observable = Observable.fromArray(letters);
       observable.subscribe( letter -> result.append(letter));
       System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

abcdefg

Example - Usage of timestamp operator

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using subscribe operator to subscribe to an Observable
public class ObservableTester {
   public static void main(String[] args) {    
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      Observable<String> observable = Observable.fromArray(letters);
      observable
         .timestamp()
         .subscribe( letter -> result.append(letter + "\n"));
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

Timed[time=1758342979382, unit=MILLISECONDS, value=a]
Timed[time=1758342979386, unit=MILLISECONDS, value=b]
Timed[time=1758342979386, unit=MILLISECONDS, value=c]
Timed[time=1758342979386, unit=MILLISECONDS, value=d]
Timed[time=1758342979386, unit=MILLISECONDS, value=e]
Timed[time=1758342979386, unit=MILLISECONDS, value=f]
Timed[time=1758342979386, unit=MILLISECONDS, value=g]

RxJava - Conditional Operators

Following are the operators which evaluates one or multiple Observables or items emitted.

Sr.No. Operator & Description
1

all

Evaluates all items emitted to meet given criteria.

2

amb

Emits all items from the first Observable only given multiple Observables.

3

contains

Checks if an Observable emits a particular item or not.

4

defaultIfEmpty

Emits default item if Observable do not emit anything.

5

sequenceEqual

Checks if two Observables emit the same sequence of items.

6

skipUntil

Discards items emitted by first Observable until a second Observable emits an item.

7

skipWhile

Discard items emitted by an Observable until a given condition becomes false.

8

takeUntil

Discards items emitted by an Observable after a second Observable emits an item or terminates.

9

takeWhile

Discard items emitted by an Observable after a specified condition becomes false.

Example - Usage of defaultIfEmpty Operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using defaultIfEmpty operator to operate on an Observable
public class ObservableTester  {
   public static void main(String[] args) {    
      final StringBuilder result = new StringBuilder();

      Observable.empty()
         .defaultIfEmpty("No Data")   
         .subscribe(s -> result.append(s));

      System.out.println(result);

      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result1 = new StringBuilder();

      Observable.fromArray(letters)
         .firstElement()
         .defaultIfEmpty("No data")   
         .subscribe(s -> result1.append(s));

      System.out.println(result1);
   }
}

Output

Compile and Run the code to verify the following output −

No Data
a

Example - Usage of contains Operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using contains operator to operate on an Observable
public class ObservableTester  {
   public static void main(String[] args) {    
      final StringBuilder result = new StringBuilder();

      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};

      
      Observable.fromArray(letters)
         .contains("c")
         .subscribe(s -> result.append(s));

      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

true

RxJava - Mathematical Operators

Following are the operators which operates on entire items emitted by an Observable.

Sr.No. Operator & Description
1

concat

Emits all items from multiple Observable without interleaving.

2

count

Counts all items and emit the result.

3

reduce

Apply a function on each item and return the result.

4

sum

Evaluates sum of all items and emit the result.

Example - Usage of count operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using count operator to operate on an Observable
public class ObservableTester  {
   public static void main(String[] args) {    
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      Observable.fromArray(letters)
         .count()   
         .subscribe(System.out::println);
   }
}

Output

Compile and Run the code to verify the following output −

7

Example - Usage of reduce operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;

//Using reduce operator to get sum of numbers
public class ObservableTester  {
   public static void main(String[] args) {    
      Observable.just(1,2,3,4,5,6,7)
         .reduce(0, (a,b) -> a + b) 
         .subscribe(s -> System.out.println("Sum: " + s));
   }
}

Output

Compile and Run the code to verify the following output −

28

RxJava - Connectable Operators



Following are the operators which has more precisely control over subscription.

Sr.No. Operator & Description
1

Connect

Instruct a connectable Observable to emit items to its subscribers.

2

Publish

Converts an Observable to connectable Observable.

3

RefCount

Converts a connectable Observable to ordinary Observable.

4

Replay

Ensure same sequence of emitted items to be seen by each subscriber, even after the Observable has begun emitting items and subscribers subscribe later.

Example - Usage of connect operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.observables.ConnectableObservable;

// Using connect operator to get connect with ConnectableObservable
public class ObservableTester  {
   public static void main(String[] args) {    
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      ConnectableObservable<String> connectable = Observable.fromArray(letters).publish();      
      connectable.subscribe(letter -> result.append(letter));
      System.out.println(result.length());
   
      connectable.connect();
      System.out.println(result.length());
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

0
7
abcdefg

Example - Usage of refCount operator

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.observables.ConnectableObservable;

// Using refCount operator to convert a ConnectableObservable to Observable
public class ObservableTester  {
   public static void main(String[] args) {    
      String[] letters = {"a", "b", "c", "d", "e", "f", "g"};
      final StringBuilder result = new StringBuilder();
      ConnectableObservable<String> connectable = Observable.fromArray(letters).publish();
      Observable<String> observable = connectable.refCount();
      observable.subscribe(letter -> result.append(letter));
      System.out.println(result.length());
      System.out.println(result);
   }
}

Output

Compile and Run the code to verify the following output −

7
abcdefg

RxJava - Subjects

As per the Reactive, a Subject can act as both Observable as well as Observer.

A Subject is a sort of bridge or proxy that is available in some implementations of ReactiveX that acts both as an observer and as an Observable. Because it is an observer, it can subscribe to one or more Observables, and because it is an Observable, it can pass through the items it observes by reemitting them, and it can also emit new items.

Types of Subjects

There are four types of Subjects −

Sr.No. Subject & Description
1

Publish Subject

Emits only those items which are emitted after time of subscription.

2 Replay Subject

Emits all the items emitted by source Observable regardless of when it has subscribed the Observable.

3

Behavior Subject

Upon subscription, emits the most recent item then continue to emit item emitted by the source Observable.

4

Async Subject

Emits the last item emitted by the source Observable after it's completes emission.

5

Unicast Subject

Queues up events until a single observer subscribes to it.

RxJava - PublishSubject

PublishSubject subject emits items to currently subscribed Observers and terminal events to current or late Observers.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.subjects.PublishSubject<T> class −

public final class PublishSubject<T>
   extends Subject<T>

Example - Usage of PublishSubject

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.subjects.PublishSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      final StringBuilder result1 = new StringBuilder();
      final StringBuilder result2 = new StringBuilder();         

      PublishSubject<String> subject = PublishSubject.create(); 
      subject.subscribe(value -> result1.append(value) ); 
      subject.onNext("a"); 
      subject.onNext("b"); 
      subject.onNext("c"); 
      subject.subscribe(value -> result2.append(value)); 
      subject.onNext("d"); 
      subject.onComplete();

      //Output will be abcd 
      System.out.println(result1);
      //Output will be d only
      //as subscribed after c item emitted.
      System.out.println(result2);
   }
}

Output

Compile and Run the code to verify the following output −

abcd
d

Example - Usage of PublishSubject events

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.annotations.NonNull;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.subjects.PublishSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      PublishSubject<String> subject = PublishSubject.create(); 

      subject.subscribe(new Observer<Object>() {

         @Override
         public void onComplete() {
            System.out.println("Observer: Completed");
         }

         @Override
         public void onError(@NonNull Throwable error) {
            System.out.println("Observer: Error" + error.getMessage());
         }

         @Override
         public void onNext(@NonNull Object item) {
            System.out.println("Observer received: " + item);
         }

         @Override
         public void onSubscribe(@NonNull Disposable arg0) {
            System.out.println("Observer: Subscribed");
         }
      });

      subject.onNext("A"); 
      subject.onNext("B");

      subject.onComplete();
   }
}

Output

Compile and Run the code to verify the following output −

Observer: Subscribed
Observer received: A
Observer received: B
Observer: Completed

RxJava - BehaviorSubject

BehaviorSubject subject emits the most recent item it has observed and then all subsequent observed items to each subscribed Observer.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.subjects.BehaviorSubject<T> class −

public final class BehaviorSubject<T>
   extends Subject<T>

Example - Usage of BehaviorSubject

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.subjects.BehaviorSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      final StringBuilder result1 = new StringBuilder();
      final StringBuilder result2 = new StringBuilder();         
      BehaviorSubject<String> subject =  BehaviorSubject.create(); 
      subject.subscribe(value -> result1.append(value) ); 
      subject.onNext("a"); 
      subject.onNext("b"); 
      subject.onNext("c"); 
      subject.subscribe(value -> result2.append(value)); 
      subject.onNext("d"); 
      subject.onComplete();
      //Output will be abcd
      System.out.println(result1);
      //Output will be cd being BehaviorSubject 
      //(c is last item emitted before subscribe)
      System.out.println(result2);
   }
}

Output

Compile and Run the code to verify the following output −

abcd
cd

Example - Usage of BehaviorSubject events

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.annotations.NonNull;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.subjects.BehaviorSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      BehaviorSubject<String> subject = BehaviorSubject.create(); 

      subject.subscribe(new Observer<Object>() {

         @Override
         public void onComplete() {
            System.out.println("Observer: Completed");
         }

         @Override
         public void onError(@NonNull Throwable error) {
            System.out.println("Observer: Error" + error.getMessage());
         }

         @Override
         public void onNext(@NonNull Object item) {
            System.out.println("Observer received: " + item);
         }

         @Override
         public void onSubscribe(@NonNull Disposable arg0) {
            System.out.println("Observer: Subscribed");
         }
      });

      subject.onNext("A"); 
      subject.onNext("B");

      subject.onComplete();
   }
}

Output

Compile and Run the code to verify the following output −

Observer: Subscribed
Observer received: A
Observer received: B
Observer: Completed

RxJava - ReplaySubject

ReplaySubject subject replays events/items to current and late Observers.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.subjects.ReplaySubject<T> class −

public final class ReplaySubject<T>
   extends Subject<T>

Example - Usage of ReplaySubject

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.subjects.ReplaySubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      final StringBuilder result1 = new StringBuilder();
      final StringBuilder result2 = new StringBuilder();         

      ReplaySubject<String> subject = ReplaySubject.create(); 
      subject.subscribe(value -> result1.append(value) ); 
      subject.onNext("a"); 
      subject.onNext("b"); 
      subject.onNext("c"); 
      subject.subscribe(value -> result2.append(value)); 
      subject.onNext("d"); 
      subject.onComplete();

      //Output will be abcd
      System.out.println(result1);
      //Output will be abcd being ReplaySubject
      //as ReplaySubject emits all the items
      System.out.println(result2);
   }
}

Output

Compile and Run the code to verify the following output −

abcd
abcd

Example - Usage of ReplaySubject events

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.annotations.NonNull;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.subjects.ReplaySubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      ReplaySubject<String> subject = ReplaySubject.create(); 

      subject.subscribe(new Observer<Object>() {

         @Override
         public void onComplete() {
            System.out.println("Observer: Completed");
         }

         @Override
         public void onError(@NonNull Throwable error) {
            System.out.println("Observer: Error" + error.getMessage());
         }

         @Override
         public void onNext(@NonNull Object item) {
            System.out.println("Observer received: " + item);
         }

         @Override
         public void onSubscribe(@NonNull Disposable arg0) {
            System.out.println("Observer: Subscribed");
         }
      });

      subject.onNext("A"); 
      subject.onNext("B");

      subject.onComplete();
   }
}

Output

Compile and Run the code to verify the following output −

Observer: Subscribed
Observer received: A
Observer received: B
Observer: Completed

RxJava - AsyncSubject

AsyncSubject emits the only last value followed by a completion event or the received error to Observers.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.subjects.AsyncSubject<T> class −

public final class AsyncSubject<T>
   extends Subject<T>

Example - Usage of AsyncSubject

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.subjects.AsyncSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      final StringBuilder result1 = new StringBuilder();
      final StringBuilder result2 = new StringBuilder();         

      AsyncSubject<String> subject =  AsyncSubject.create(); 
      subject.subscribe(value -> result1.append(value) ); 
      subject.onNext("a"); 
      subject.onNext("b"); 
      subject.onNext("c"); 
      subject.subscribe(value -> result2.append(value)); 
      subject.onNext("d"); 
      subject.onComplete();

      //Output will be d being the last item emitted
      System.out.println(result1);
      //Output will be d being the last item emitted     
      System.out.println(result2);
   }
}

Output

Compile and Run the code to verify the following output −

d
d

Example - Usage of AsyncSubject events

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.annotations.NonNull;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.subjects.AsyncSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      AsyncSubject<String> subject = AsyncSubject.create(); 

      subject.subscribe(new Observer<Object>() {

         @Override
         public void onComplete() {
            System.out.println("Observer: Completed");
         }

         @Override
         public void onError(@NonNull Throwable error) {
            System.out.println("Observer: Error" + error.getMessage());
         }

         @Override
         public void onNext(@NonNull Object item) {
            System.out.println("Observer received: " + item);
         }

         @Override
         public void onSubscribe(@NonNull Disposable arg0) {
            System.out.println("Observer: Subscribed");
         }
      });

      subject.onNext("A"); 
      subject.onNext("B");

      subject.onComplete();
   }
}

Output

Compile and Run the code to verify the following output −

Observer: Subscribed
Observer received: B
Observer: Completed

RxJava - UnicastSubject

UnicastSubject queues up events until a single Observer subscribes to it, replays those events to it until the Observer picks up and then subject switches to relaying events live to this single Observer until this UnicastSubject terminates or the Observer disposes of.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.subjects.UnicastSubject<T> class −

public final class UnicastSubject<T>
   extends Subject<T>

Example - Usage of UnicastSubject

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.subjects.UnicastSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      final StringBuilder result1 = new StringBuilder();
      final StringBuilder result2 = new StringBuilder();         

      UnicastSubject<String> subject =  UnicastSubject.create(); 
      subject.subscribe(value -> result1.append(value) ); 
      subject.onNext("a"); 
      subject.onNext("b"); 
      subject.onNext("c"); 
      // error will be thrown as only single observer is allowed.
      subject.subscribe(value -> result2.append(value)); 
      subject.onNext("d"); 
      subject.onComplete();

      //Output will be d being the last item emitted
      System.out.println(result1);
      //Output will be d being the last item emitted     
      System.out.println(result2);
   }
}

Output

Compile and Run the code to verify the following output −

io.reactivex.rxjava3.exceptions.OnErrorNotImplementedException: The exception was not handled due to missing onError handler in the subscribe() method call. Further reading: https://github.com/ReactiveX/RxJava/wiki/Error-Handling | java.lang.IllegalStateException: Only a single observer allowed.
	at io.reactivex.rxjava3.internal.functions.Functions$OnErrorMissingConsumer.accept(Functions.java:718)
	at io.reactivex.rxjava3.internal.functions.Functions$OnErrorMissingConsumer.accept(Functions.java:715)
	at io.reactivex.rxjava3.internal.observers.LambdaObserver.onError(LambdaObserver.java:77)
	at io.reactivex.rxjava3.internal.disposables.EmptyDisposable.error(EmptyDisposable.java:63)
	at io.reactivex.rxjava3.subjects.UnicastSubject.subscribeActual(UnicastSubject.java:294)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13263)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13208)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13146)
	at com.tutorialspoint.ObservableTester.main(ObservableTester.java:16)
Caused by: java.lang.IllegalStateException: Only a single observer allowed.
	... 5 more
Exception in thread "main" io.reactivex.rxjava3.exceptions.OnErrorNotImplementedException: The exception was not handled due to missing onError handler in the subscribe() method call. Further reading: https://github.com/ReactiveX/RxJava/wiki/Error-Handling | java.lang.IllegalStateException: Only a single observer allowed.
	at io.reactivex.rxjava3.internal.functions.Functions$OnErrorMissingConsumer.accept(Functions.java:718)
	at io.reactivex.rxjava3.internal.functions.Functions$OnErrorMissingConsumer.accept(Functions.java:715)
	at io.reactivex.rxjava3.internal.observers.LambdaObserver.onError(LambdaObserver.java:77)
	at io.reactivex.rxjava3.internal.disposables.EmptyDisposable.error(EmptyDisposable.java:63)
	at io.reactivex.rxjava3.subjects.UnicastSubject.subscribeActual(UnicastSubject.java:294)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13263)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13208)
	at io.reactivex.rxjava3.core.Observable.subscribe(Observable.java:13146)
	at com.tutorialspoint.ObservableTester.main(ObservableTester.java:16)
Caused by: java.lang.IllegalStateException: Only a single observer allowed.
	... 5 more
abcd

Example - Usage of UnicastSubject events

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.annotations.NonNull;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.subjects.UnicastSubject;

public class ObservableTester  {
   public static void main(String[] args) {   
      UnicastSubject<String> subject = UnicastSubject.create(); 

      subject.subscribe(new Observer<Object>() {

         @Override
         public void onComplete() {
            System.out.println("Observer: Completed");
         }

         @Override
         public void onError(@NonNull Throwable error) {
            System.out.println("Observer: Error" + error.getMessage());
         }

         @Override
         public void onNext(@NonNull Object item) {
            System.out.println("Observer received: " + item);
         }

         @Override
         public void onSubscribe(@NonNull Disposable arg0) {
            System.out.println("Observer: Subscribed");
         }
      });

      subject.onNext("A"); 
      subject.onNext("B");

      subject.onComplete();
   }
}

Output

Compile and Run the code to verify the following output −

Observer: Subscribed
Observer received: A
Observer received: B
Observer: Completed

RxJava - Schedulers

Schedulers are used in multi-threading environment to work with Observable operators.

As per the Reactive,Scheduler are used to schedule how chain of operators will apply to different threads.

By default, an Observable and the chain of operators that you apply to it will do its work, and will notify its observers, on the same thread on which its Subscribe method is called. The SubscribeOn operator changes this behavior by specifying a different Scheduler on which the Observable should operate. The ObserveOn operator specifies a different Scheduler that the Observable will use to send notifications to its observers.

Types of Schedulers

There are following types of Schedulers available in RxJava −

Sr.No. Scheduler & Description
1

Schedulers.computation()

Creates and returns a Scheduler intended for computational work. Count of threads to be scheduled depends upon the CPUs present in the system. One thread is allowed per CPU. Best for event-loops or callback operations.

2

Schedulers.io()

Creates and returns a Scheduler intended for IO-bound work. Thread pool may extend as needed.

3

Schedulers.newThread()

Creates and returns a Scheduler that creates a new Thread for each unit of work.

4

Schedulers.trampoline()

Creates and returns a Scheduler that queues work on the current thread to be executed after the current work completes.

5

Schedulers.from(java.util.concurrent.Executor executor)

Converts an Executor into a new Scheduler instance.

RxJava - Trampoline Scheduler

Schedulers.trampoline() method creates and returns a Scheduler that queues work on the current thread to be executed after the current work completes.

Example - Usage of Schedulers.trampoline()

ObservableTester.java

package com.tutorialspoint;

import java.util.Random;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args) throws InterruptedException {
      Observable.just("A", "AB", "ABC")
         .flatMap(v -> getLengthWithDelay(v)
         .doOnNext(s -> System.out.println("Processing Thread " 
            + Thread.currentThread().getName()))
         .subscribeOn(Schedulers.trampoline()))
         .subscribe(length -> System.out.println("Receiver Thread " 
            + Thread.currentThread().getName() 
            + ", Item length " + length));

         Thread.sleep(10000);
   }
   protected static Observable<Integer> getLengthWithDelay(String v) {
      Random random = new Random();
      try {
         Thread.sleep(random.nextInt(3) * 1000);
         return Observable.just(v.length());
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      return null;
   }
}

Output

Compile and Run the code to verify the following output −

Processing Thread main
Receiver Thread main, Item length 1
Processing Thread main
Receiver Thread main, Item length 2
Processing Thread main
Receiver Thread main, Item length 3

RxJava - NewThread Scheduler

Schedulers.newThread() method creates and returns a Scheduler that creates a new Thread for each unit of work.

Example - Usage of Schedulers.newThread()

ObservableTester.java

package com.tutorialspoint;

import java.util.Random;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args) throws InterruptedException {
      Observable.just("A", "AB", "ABC")
         .flatMap(v -> getLengthWithDelay(v)
         .doOnNext(s -> System.out.println("Processing Thread " 
            + Thread.currentThread().getName()))
         .subscribeOn(Schedulers.newThread()))
         .subscribe(length -> System.out.println("Receiver Thread " 
            + Thread.currentThread().getName() 
            + ", Item length " + length));

         Thread.sleep(10000);
   }
   protected static Observable<Integer> getLengthWithDelay(String v) {
      Random random = new Random();
      try {
         Thread.sleep(random.nextInt(3) * 1000);
         return Observable.just(v.length());
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      return null;
   }
}

Output

Compile and Run the code to verify the following output −

Processing Thread RxNewThreadScheduler-1
Receiver Thread RxNewThreadScheduler-1, Item length 1
Processing Thread RxNewThreadScheduler-2
Receiver Thread RxNewThreadScheduler-2, Item length 2
Processing Thread RxNewThreadScheduler-3
Receiver Thread RxNewThreadScheduler-3, Item length 3

RxJava - Computation Scheduler

The Completable class represents deferred response. Completable observable can either indicate a successful completion or error.

Class Declaration

Following is the declaration for io.reactivex.rxjava3.core.Completable<T> class −

public abstract class Completable
   extends Object
      implements CompletableSource

Protocol

Following is the sequential protocol that Single Observable operates −

onSubscribe (onError | OnComplete)?

Example - Creating a Completable Observable Class to get Data

ObservableTester.java

package com.tutorialspoint;

import io.reactivex.rxjava3.core.Completable;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      Completable.complete().doOnComplete(() -> System.out.println("Hello World")).subscribe();
   }
}

Output

Compile and Run the code to verify the following output −

Hello World

Example - Usage of Completable Observable Class to get Data after a delay of 2 seconds

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Completable;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.observers.DisposableCompletableObserver;
import io.reactivex.rxjava3.schedulers.Schedulers;


public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {

      //Create an observer
      Disposable disposable = Completable.complete()
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .subscribeWith(new DisposableCompletableObserver() {
         @Override
         public void onError(Throwable e) { 
            e.printStackTrace();
         }
         @Override
         public void onStart() {
            System.out.println("Started!");
         }
         @Override
         public void onComplete() {
            System.out.println("Done!");
         }
      }); 
      Thread.sleep(3000);
      //start observing
      disposable.dispose();
   }
}

Output

Compile and Run the code to verify the following output −

Started!
Done!

RxJava - IO Scheduler

Schedulers.io() method creates and returns a Scheduler intended for IO-bound work. Thread pool may extend as needed. Best for I/O intensive operations.

Example - Usage of Schedulers.io()

ObservableTester.java

package com.tutorialspoint;

import java.util.Random;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args) throws InterruptedException {
      Observable.just("A", "AB", "ABC")
         .flatMap(v -> getLengthWithDelay(v)
         .doOnNext(s -> System.out.println("Processing Thread " 
            + Thread.currentThread().getName()))
         .subscribeOn(Schedulers.io()))
         .subscribe(length -> System.out.println("Receiver Thread " 
            + Thread.currentThread().getName() 
            + ", Item length " + length));

         Thread.sleep(10000);
   }
   protected static Observable<Integer> getLengthWithDelay(String v) {
      Random random = new Random();
      try {
         Thread.sleep(random.nextInt(3) * 1000);
         return Observable.just(v.length());
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      return null;
   }
}

Output

Compile and Run the code to verify the following output −

Processing Thread RxCachedThreadScheduler-1
Receiver Thread RxCachedThreadScheduler-1, Item length 1
Processing Thread RxCachedThreadScheduler-1
Receiver Thread RxCachedThreadScheduler-1, Item length 2
Processing Thread RxCachedThreadScheduler-2
Receiver Thread RxCachedThreadScheduler-2, Item length 3

RxJava - From Scheduler

Schedulers.from(Executor) method converts an Executor into a new Scheduler instance.

Example - Usage of Schedulers.from()

ObservableTester.java

package com.tutorialspoint;

import java.util.Random;
import java.util.concurrent.Executors;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester  {
   public static void main(String[] args) throws InterruptedException {
      Observable.just("A", "AB", "ABC")
         .flatMap(v -> getLengthWithDelay(v)
         .doOnNext(s -> System.out.println("Processing Thread " 
            + Thread.currentThread().getName()))
         .subscribeOn(Schedulers.from(Executors.newFixedThreadPool(3))))
         .subscribe(length -> System.out.println("Receiver Thread " 
            + Thread.currentThread().getName() 
            + ", Item length " + length));

         Thread.sleep(10000);
   }
   protected static Observable<Integer> getLengthWithDelay(String v) {
      Random random = new Random();
      try {
         Thread.sleep(random.nextInt(3) * 1000);
         return Observable.just(v.length());
      } catch (InterruptedException e) {
         e.printStackTrace();
      }
      return null;
   }
}

Output

Compile and Run the code to verify the following output −

Processing Thread pool-1-thread-1
Receiver Thread pool-1-thread-1, Item length 1
Processing Thread pool-3-thread-1
Receiver Thread pool-3-thread-1, Item length 2
Processing Thread pool-4-thread-1
Receiver Thread pool-4-thread-1, Item length 3

RxJava - Buffering

Buffering operator allows to gather items emitted by an Observable into a list or bundles and emit those bundles instead of items. In the example below, we've created an Observable to emit 9 items and using buffering, 3 items will be emitted together.

Example - Usage of Buffering Operator

ObservableTester.java

package com.tutorialspoint;

import java.util.List;
import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      Observable<Integer> observable = Observable.just(1, 2, 3, 4,
         5, 6, 7, 8, 9);

      observable.subscribeOn(Schedulers.io())
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .buffer(3)
         .subscribe(new Observer<List<Integer>>() {
            @Override
            public void onSubscribe(Disposable d) {
               System.out.println("Subscribed");
            }
            @Override
            public void onNext(List<Integer> integers) {
               System.out.println("onNext: ");
               for (Integer value : integers) {
                  System.out.println(value);
               }
            }
            @Override
            public void onError(Throwable e) {
               System.out.println("Error");
            }

            @Override
            public void onComplete() {
               System.out.println("Done! ");
            }
         });
      Thread.sleep(3000);
   }
}

Output

Compile and Run the code to verify the following output −

Subscribed
onNext: 
1
2
3
onNext: 
4
5
6
onNext: 
7
8
9
Done! 

RxJava - Windowing

Windowing operator works similar to buffer operator but it allows to gather items emitted by an Observable into another observable instead of collection and emit those Observables instead of collections. In the example below, we've created an Observable to emit 9 items and using window operator, 3 Observable will be emitted together.

Example - Usage of Windowing Operator

ObservableTester.java

package com.tutorialspoint;

import java.util.concurrent.TimeUnit;

import io.reactivex.rxjava3.core.Observable;
import io.reactivex.rxjava3.core.Observer;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.schedulers.Schedulers;

public class ObservableTester {
   public static void main(String[] args) throws InterruptedException {
      Observable<Integer> observable = Observable.just(1, 2, 3, 4,
         5, 6, 7, 8, 9);

      observable.subscribeOn(Schedulers.io())
         .delay(2, TimeUnit.SECONDS, Schedulers.io())
         .window(3)
         .subscribe(new Observer<Observable<Integer>>() {
            @Override
            public void onSubscribe(Disposable d) {
               System.out.println("Subscribed");
            }
            @Override
            public void onNext(Observable<Integer> integers) {
               System.out.println("onNext: ");
               integers.subscribe(value -> System.out.println(value));
            }
            @Override
            public void onError(Throwable e) {
               System.out.println("Error");
            }

            @Override
            public void onComplete() {
               System.out.println("Done! ");
            }
         });
      Thread.sleep(3000);
   }
}

Output

Compile and Run the code to verify the following output −

Subscribed
onNext: 
1
2
3
onNext: 
4
5
6
onNext: 
7
8
9
Done! 
Advertisements