- Introduction
- Out Of Scope
- Explanation Declarative Approach
- Explanation Functional Interface
- Explanation Callback
- Explanation Consumer
- Explanation Function
- Explanation Optional
- Explanation Predicate
- Explanation Supplier
- Explanation Lambdas
- Explanation Map
- Explanation Stream
- Explanation Parallel Stream
- Explanation Combinator Pattern
- Explanation Other important Points
- Technologies Used
- Prerequisities
- Commands
- References
- Contact Information
The aim of this project is to show case the differences between Imperative and declarative approach of coding. Another focus is on different functions available in the Stream API as well as some pros and cons of some of these approaches.
Since only basic implementation of various functions from stream API is targeted for this project and the main idea is just to see them in action, unit tests are out of scope.
Our normal approach before Java 8 was to program via Imperative Programming but lambdas work via Declarative programming.
Declarative programming: Declarative programming is a programming paradigm that expresses the logic of a computation without describing its control flow. In simple words, Declarative Programming is like asking your friend to draw a landscape. You don’t care how they draw it, that’s up to them.
whereas
Imperative Programming: imperative programming is a programming paradigm that uses statements that changes a program's state. In simple words, Imperative Programming is like your friend listening to Bob Ross telling them how to paint a landscape. While good ole Bob Ross isn’t exactly commanding, he is giving them step by step directions to get the desired result.
A functional interface is an interface which has exactly one abstract method.
Please note the following from JavaDoc:
Since default methods have an implementation, they are not abstract. If an interface declares an abstract method overriding one of the public methods of java.lang.Object, that also does not count toward the interface's abstract method count since any implementation of the interface will have an implementation from java.lang.Object or elsewhere.
Let us see the six basic function interfaces.
Interface | Signature | Examples |
---|---|---|
UnaryOperator T | apply(T t) | String::toLowerCase, Math::tan |
BinaryOperator T | apply(T t1, T t2) | BigInteger::add, Math::pow |
Function<T, R> R | apply(T t) | Arrays::asList, Integer::toBinaryString |
Predicate<T, U> boolean | test(T t, U u) | String::isEmpty, Character::isDigit |
Supplier T | get() | LocalDate::now, Instant::now |
Consumer void | accept(T t) | System.out::println, Error::printStackTrace |
Rules for functional programming
Pure functional programming has a set of rules that one must follow:
- No state, meaning that the function must not depend on or change the state of a variable/object outside the boundary of the function.
- Pure functions, meaning that the function should have everything encapsulated within it and it should not depend on something outside the boundary of the function, for example, some form of global state.
- No side effects outside of the boundary of the function.
- Higher order functions: A function is considered a higher order functions if one of the following two conditions is true.
- The function takes one or more functions as parameters. For example, Callback
- The function returns another function as result. For example, combinator pattern.
A callback is some code that you pass to a given method, so that it can be called at a later time.
Reference: The source code for the Callback is present in Callback.java class.
- Consumer: Represents an operation that accepts a single input argument and returns no result. It is similar to a void function when compared to imperative implementation.
This is implemented is Consumer class in the project. In the consumer class, a consumer object is created which takes Customer as input and prints the information on the command line. In the main method, the consumer is called via accept() function.
Similar to Consumer, one can also create BiConsumer which takes two parameters as input(instead of one) but like consumer does not return any output.
Reference: The source code for the Consumer is present in _Consumer.java class.
- Add a picture linking imperative and declarative approach together.
- Add a picture linking imperative and declarative approach together.
- Add a picture linking imperative and declarative approach together.
- Add a picture linking imperative and declarative approach together.
- Add a picture linking imperative and declarative approach together.
- To be defined
- To be defined
- To be defined
- To be defined
- To be defined
-
Created a simple maven project.
-
My project was not compiling, so I added the properties for 1.8 version as indicated in this link: https://facingissuesonit.com/2021/05/08/maven-error-source-option-5-is-no-longer-supported-use-6-or-later/
-
A stream allows us to get in an abstract mode where we simple tell it what we want.
-
Examples of functional programming:
// Assignment context Predicate p = String::isEmpty; Here we specify the predicate as an empty string . Similar to String p="";
// Method invocation context stream.filter(e -> e.getSize() > 10)... Here e--> is the return type e.size()>10 is the logic of the method
// Cast context stream.map((ToIntFunction) e -> e.getSize())... Here, (ToIntFunction) is used to transform the return type to Integer.
- Java 11
- To be defined
- To be defined
- To be defined
- 1: Java functional package (JavaDoc)
- 2: Java Stream (JavaDoc)
- 3: Functional Programming in Java - Full Course (YouTube)
- 4: Java Optionals | Crash Course (YouTube)
- 5: Get a Taste of Lambdas and Get Addicted to Streams by Venkat Subramaniam (Youtube)
- 6: Java 8 STREAMS Tutorial (YouTube)
- 7: Declarative vs Imperative Programming
- 8: Java 8 Tutorials(From Mkyong)
- 9: What is a callback function?
How to reach me? At github specific gmail account. Additionally, you can reach me via Linkedin or at Xing