In depth analysis of lambda expression of new features of jdk8
The first time I contacted lambda expression was in typescript (superset of JavaScript). At that time, it was used outside this method of typescript rather than inside this method. After using it, I suddenly thought that lambda is not a heavyweight new feature of jdk8? So I felt that I could check the relevant information and record it:
I Behavior parameterization
Behavior parameterization simply means that the main body of the function only contains the general code of the template class, and some logic that will change with the business scenario is passed to the function in the form of parameters. Using behavior parameterization can make the program more general to meet the requirements of frequent changes.
Consider a business scenario. Suppose we need to filter apples through programs, we first define an apple entity:
The initial demand of users may simply hope to screen out green apples through the program, so we can quickly realize it through the program:
This code is very simple, there is nothing worth saying. However, if the user's demand turns green, it seems that it is also very simple to modify the code, which is nothing more than changing the green of the judgment condition to red. But we need to consider another question. What if the changing conditions change frequently? If only the color is changed, let's directly let the user pass in the color judgment conditions, and the parameters of the judgment method change to "the set to be judged and the color to be filtered". But what if the user not only judges the color, but also wants to judge the weight, size and so on? Do you think we can add different parameters to complete the judgment in turn? But is this really good by passing parameters? If there are more and more screening conditions and the combination mode is more and more complex, do we need to consider all situations and have corresponding countermeasures for each situation? At this time, we can parameterize the behavior, extract the filter conditions and pass them in as parameters. At this time, we can encapsulate a judgment interface:
After the above behavior is abstracted, we can set the filter condition at the specific call place and pass the condition as a parameter to the method. At this time, the method of anonymous inner class is adopted:
Such a design is often used within the JDK, such as Java util. Comparator,java. util. concurrent. Callable, etc. when using this kind of interface, we can use anonymous classes to specify the specific execution logic of the function at the specific call place. However, from the above code block, although it is very geek, it is not concise enough. In java8, we can simplify it through lambda:
II Lambda expression definition
We can define a lambda expression as a concise and transitive anonymous function. First, we need to make it clear that a lambda expression is essentially a function. Although it does not belong to a specific class, it has a parameter list, function body, return type, and can throw exceptions; Secondly, it is anonymous, and the lambda expression has no specific function name; Lambda expressions can be passed like parameters, which greatly simplifies the writing of code. The format is defined as follows:
Format 1: parameter list - > expression
Format 2: parameter list - > {expression set}
It should be noted that the lambda expression implies the return keyword, so we do not need to explicitly write the return keyword in a single expression, but when the expression is a statement set, we need to explicitly add a return and surround multiple expressions with curly braces {}. Here are some examples:
III Using lambda expressions relying on functional interfaces
The use of lambda expression needs the help of functional interface, that is, we can simplify it with lambda expression only where functional interface appears.
Custom functional interface:
A functional interface is defined as an interface with only one abstract method. The improvement of java8 in interface definition is the introduction of default methods, so that we can provide default implementation of methods in the interface. However, no matter how many default methods exist, as long as there is one and only one abstract method, it is a functional interface, as follows (refer to applefilter above):
Applefilter only contains an abstract method accept (apple apple apple). According to the definition, it can be regarded as a functional interface. During the definition, we added @ functionalinterface annotation for the interface to mark that the interface is a functional interface, but the interface is optional. After adding the interface, the compiler restricts the interface to only one abstract method, Otherwise, an error is reported, so it is recommended to add this annotation for functional interfaces.
JDK's own functional interface:
JDK has built-in rich functional interfaces for lambda expressions. The following are examples of predict < T >, consumer < T >, and function < T, R >.
Predicate:
The function of predicate is similar to the applefilter above. We use the conditions we set externally to verify the incoming parameters and return the verification result Boolean. Next, we use predicate to filter the elements of the list set:
use:
Consumer
Consumer provides an accept abstract function, which receives parameters but does not return values. Next, use consumer to traverse the collection
Use the above functional interface to traverse the string set and print non empty strings:
Function
Function performs the conversion operation. The input is the data of type T and the return is the data of type R. next, use function to convert the collection:
other:
The above functional interfaces also provide the default implementation of some logical operations, which will be left to the later introduction of the default methods of the Java 8 interface~
Some matters needing attention during use:
Type inference:
During coding, we may sometimes wonder which functional interface our calling code will match. In fact, the compiler will make correct decisions according to parameters, return types, exception types (if any). During specific calls, the type of parameters can be omitted at some times to further simplify the code:
local variable
In all the above examples, our lambda expression uses its main parameters, and we can also use local variables in lambda, as follows
In this example, we use the local variable weight in lambda. However, when using the local variable in lambda, it must be explicitly declared as final or in fact final. This is mainly because the local variable is stored on the stack and the lambda expression runs in another thread. When the thread view accesses the local variable, This variable may be changed or recycled, so there will be no thread safety problem after final modification.
IV Method reference
Using method reference can further simplify the code. Sometimes this simplification makes the code look more intuitive. Let's take a look at an example first:
Method reference connects method membership and method itself, which is mainly divided into three categories:
Static method
convert to
Instance method of parameter
convert to
External instance method
convert to
reference resources:
http://www.codeceo.com/article/lambda-of-java-8.html
The above is the lambda expression of the new features of jdk8 introduced by Xiaobian. I hope it will be helpful to you. If you have any questions, please leave me a message and Xiaobian will reply to you in time. Thank you very much for your support for the programming tips website!