Lambda expressions
Lambda is an anonymous function, and we can think of a Lambda expression as a piece of code that can be passed (passing code like data). It can be used to write more concise, more flexible code, as a more compact code generation style, so that the Java language expression ability has been improved.
Lambda expressions are a new syntax element and operator introduced in the Java8 language. The “->” operator is called the Lambda operator or arrow operator, which divides Lambda into two parts:
- Left: specified
Lambda
A list of arguments required by the expression - Right: Specified
Lambda
The body is the implementation logic of the abstract method, i.eLambda
The function to be performed by the expression.
import org.junit.Test;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.function.Consumer;
/** * pare(o1,o2) -> integer.pare (o1, O2); * 2. Format: * -> :lambda operator or arrow operator * -> Left :lambda parameter list (which is the abstract method parameter list in the interface) * -> Right: * <p> * 3. Use of lambda expressions: (divided into 6 cases) * <p> * Summary: * -> Left: the type of lambda parameter list can be omitted (type inference); If the lambda parameter list has only one argument, one pair of () can also be omitted * -> to the right: the lambda body should be wrapped with a pair of {}; If the lambda body has only one execution statement (possibly a return statement), omit this pair of {} and the return keyword * <p> * 4. The essence of a lambda expression: as an instance of a functional interface * <p> * 5. An interface that declares only one abstract method is called a functional interface. We can use it on one interface@FunctionalInterface Annotation, * To check if it is a functional interface. * <p> * 6. So everything previously represented by anonymous implementation classes can now be written as Lambda expressions. * /
public class LambdaTest1 {
// Syntax format 1: no parameter, no return value
@Test
public void test1() {
Runnable r1 = new Runnable() {
@Override
public void run() {
System.out.println("I love Tiananmen Square in Beijing"); }}; r1.run(); System.out.println("* * * * * * * * * * * * * * * * * * * * * * *");
Runnable r2 = () -> {
System.out.println("I love the Forbidden City in Beijing");
};
r2.run();
}
Lambda takes one argument, but returns no value.
@Test
public void test2() {
Consumer<String> con = new Consumer<String>() {
@Override
public void accept(String s){ System.out.println(s); }}; con.accept("What's the difference between a lie and an oath?");
System.out.println("* * * * * * * * * * * * * * * * * * *");
Consumer<String> con1 = (String s) -> {
System.out.println(s);
};
con1.accept("One is listening to people seriously, and the other is talking to people seriously.");
}
// Data types can be omitted because they can be inferred by the compiler, called "type inference"
@Test
public void test3() {
Consumer<String> con1 = (String s) -> {
System.out.println(s);
};
con1.accept("One is listening to people seriously, and the other is talking to people seriously.");
System.out.println("* * * * * * * * * * * * * * * * * * *");
Consumer<String> con2 = (s) -> {
System.out.println(s);
};
con2.accept("One is listening to people seriously, and the other is talking to people seriously.");
}
@Test
public void test4() {
ArrayList<String> list = new ArrayList<>();// Type inference
int[] arr = {1.2.3};// Type inference
}
If Lambda requires only one argument, the parentheses of the argument can be omitted
@Test
public void test5() {
Consumer<String> con1 = (s) -> {
System.out.println(s);
};
con1.accept("One is listening to people seriously, and the other is talking to people seriously.");
System.out.println("* * * * * * * * * * * * * * * * * * *");
Consumer<String> con2 = s -> {
System.out.println(s);
};
con2.accept("One is listening to people seriously, and the other is talking to people seriously.");
}
Lambda takes two or more arguments, multiple execution statements, and can have a return value
@Test
public void test6() {
Comparator<Integer> com1 = new Comparator<Integer>() {
@Override
public int compare(Integer o1, Integer o2) {
System.out.println(o1);
System.out.println(o2);
returno1.compareTo(o2); }}; System.out.println(com1.compare(12.21));
System.out.println("* * * * * * * * * * * * * * * * * * * * * * * * * * * * *");
Comparator<Integer> com2 = (o1, o2) -> {
System.out.println(o1);
System.out.println(o2);
return o1.compareTo(o2);
};
System.out.println(com2.compare(12.6));
}
// If the Lambda body has only one statement, the return and braces, if present, can be omitted
@Test
public void test7() {
Comparator<Integer> com1 = (o1, o2) -> {
return o1.compareTo(o2);
};
System.out.println(com1.compare(12.6));
System.out.println("* * * * * * * * * * * * * * * * * * * * * * * * * * * * *");
Comparator<Integer> com2 = (o1, o2) -> o1.compareTo(o2);
System.out.println(com2.compare(12.21));
}
@Test
public void test8() {
Consumer<String> con1 = s -> {
System.out.println(s);
};
con1.accept("One is listening to people seriously, and the other is talking to people seriously.");
System.out.println("* * * * * * * * * * * * * * * * * * * * * * * * * * * * *");
Consumer<String> con2 = s -> System.out.println(s);
con2.accept("One is listening to people seriously, and the other is talking to people seriously."); }}Copy the code
Built-in four function interfaces
Consumer interface
: Consumer< T> void accept(T T) abstract method with arguments, no return value;
/** * consumer interface */
public class ConsumerInterface {
public static void main(String[] args) {
Consumer<String> stringConsumer = new Consumer<String>() {
@Override
public void accept(String str){ System.out.println(str); }};//Lambda expressions are simplified
Consumer<String> consumer =(str)->{System.out.println(str); }; consumer.accept("Print STR"); }}Copy the code
Supply interface
: Supplier < T> T get() An abstract method with no arguments and a return value;
/** ** supply interface */
public class SupplierInterface {
public static void main(String[] args) {
Supplier<String> supplier = new Supplier<String>() {
@Override
public String get() {
return "Supply interface"; }};//Lambda expressions are simplified
Supplier<String> sp =()->{return "Supply interface"; }; System.out.println(sp.get()); }Copy the code
Stereotyped interface
Predicate Boolean test(T T): takes arguments, but the return value type is fixed Boolean;
/** * Predicate * takes an input parameter and can only return a Boolean value for judgment */
public static void main(String[] args) {
// Can be used to determine whether the string is empty
Predicate pc = new Predicate<String>() {
@Override
public boolean test(String str) {
returnstr.isEmpty(); }}; System.out.println(pc.test("qwew"));
//Lambda expressions are simplified
Predicate<String> pre =(str)->{return str.isEmpty(); };
System.out.println(pre.test(""));
}
Copy the code
Functional interface
: Function<T,R> R apply(T T);
/** * Function * returns a value */
public static void main(String[] args) {
Function function = new Function<String.String> () {
@Override
public String apply(String str) {
returnstr; }};//Lambda expressions are simplified
Function<String.String> function2 = (str) -> {return str; };
System.out.println(function2.apply("asd"));
}
Copy the code
The Stream flow
We can use java.util.Stream to do various operations on a collection of one or more elements. These operations may be intermediate operations or terminal operations. The terminal operation returns a result, and the intermediate operation returns a Stream.
Stream method description
forEach
The forEach() method iterates through the elements in the stream
void forEach(Consumer<? super T> action)
List<String> list = new ArrayList<>();
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.stream().forEach((str)->{
System.out.println(str);
});
/ / short
list.stream().forEach(System.out::println);
Copy the code
Filter
Filter Filters out elements that meet the specified criteria
public static void main(args[]){
List languages = Arrays.asList("Java"."Scala"."C++"."Haskell"."Lisp");
System.out.println("Languages which starts with J :");
filter(languages, (str)->str.startsWith("J"));
System.out.println("Languages which ends with a ");
filter(languages, (str)->str.endsWith("a"));
System.out.println("Print all languages :");
filter(languages, (str)->true);
System.out.println("Print no language : ");
filter(languages, (str)->false);
System.out.println("Print language whose length greater than 4:");
filter(languages, (str)->str.length() > 4);
}
public static void filter(List names, Predicate condition) {
names.stream().filter((name) -> (condition.test(name))).forEach((name) -> {
System.out.println(name + "");
});
}
Copy the code
Predicate
// You can combine the Predicate with logical functions and(), or(), and xor(),
For example, to find all the four-letter names that start with J, you can combine the two Predicate classes and pass them in
Predicate<String> startsWithJ = (n) -> n.startsWith("J");
Predicate<String> fourLetterLong = (n) -> n.length() == 4;
names.stream()
.filter(startsWithJ.and(fourLetterLong))
.forEach((n) -> System.out.print("nName, which starts with 'J' and four letter long is : " + n));
Copy the code
limit
Filter the first n elements from the stream
Stream<T> limit(long maxSize);
// Filter out the first two elements in the stream
list.stream().limit(2).forEach(System.out::println);
Copy the code
map
The map() method maps elements in a stream to another stream
// This method requires a function-type interface to convert data of type T in the current stream into a stream of type R
<R> Stream<R> map(Function<? super T, ? extends R> mapper);
Copy the code
public static void main(String[] args) {
Stream.of("1"."2"."3"."4"."5")
.map(Integer::parseInt)
.forEach(System.out::println);
Stream.of(6.7.8.9.10)
.map(String::valueOf)
.forEach(System.out::println);
}
Copy the code
skip
Skip the first n elements and intercept
Stream<T> skip(long n);
Copy the code
Use:
public static void main(String[] args) {
Stream.of("a"."b"."c"."d"."a"."b"."a"."c")
.skip(5)
/ /. Skip (1) an error
//.skip(10)
.forEach(System.out::println);
}
Copy the code
concat
The concat() method, a static method in the Stream interface, merges two streams
public static <T> Stream<T> concat(Stream<? extends T> a, Stream<? extends T> b) {
Objects.requireNonNull(a);
Objects.requireNonNull(b);
@SuppressWarnings("unchecked")
Spliterator<T> split = new Streams.ConcatSpliterator.OfRef<>(
(Spliterator<T>) a.spliterator(), (Spliterator<T>) b.spliterator());
Stream<T> stream = StreamSupport.stream(split, a.isParallel() || b.isParallel());
return stream.onClose(Streams.composedClose(a, b));
}
Copy the code
Use:
List<Integer> list = new ArrayList<>();
list.add(12);
list.add(8);
list.add(4);
list.add(13);
Stream<Integer> stream1 = list.stream().filter((str) -> {
return str > 12;
});
Stream<Integer> stream2 = list.stream().filter((str) -> {
return str < 5;
});
Stream.concat(stream1, stream2).forEach(System.out::println); / / 13 April
Copy the code
reduce
Sum up all the data into one number
T reduce(T identity, BinaryOperator<T> accumulator);
Copy the code
Use:
public static void main(String[] args) {
Integer sum = Stream.of("1"."2"."3"."4"."5"."1"."1"."2")
.map(Integer::parseInt)
// identity: default value
// The first time the default value is assigned to a
// Each time after that, the last result is assigned to A, and B receives the data in the stream
.reduce(0, (a, b) -> {
System.out.print("a = " + a);
System.out.println(" b = " + b);
return a + b;
});
System.out.println("sum = " + sum);
// Get the maximum value:
Integer max = Stream.of("1"."2"."3"."4"."5")
.map(Integer::parseInt)
.reduce(0, (a, b) -> a > b ? a : b);
//.reduce(1, Math::max);
System.out.println("max = "+max);
// Count the number of occurrences of 1
Integer count = Stream.of("1"."2"."3"."4"."5"."1"."1"."2")
.map(s -> "1".equals(s) ? 1 : 0)
.reduce(0.Integer::sum);
System.out.println(count);
}
Copy the code
max,min
Max: Obtains the maximum value
Optional<T> max(Comparator<? super T> comparator);
Copy the code
Min: obtains the minimum value
Optional<T> min(Comparator<? super T> comparator);
Copy the code
Use:
public static void main(String[] args) {
Optional<Integer> max = Stream.of("1"."2"."3"."4"."5")
.map(Integer::parseInt)
.max(Comparator.comparingInt(o -> o));
// .max((o1,o2)->o1-o2); equivalent
System.out.println("max = "+max.get());
Optional<Integer> min = Stream.of("1"."2"."3"."4"."5")
.map(Integer::parseInt)
.min((o1,o2)->o1-o2);
System.out.println("min = "+min.get());
}
Copy the code
distinct
Remove duplicate elements
Stream<T> distinct();
Copy the code
Use:
public static void main(String[] args) {
Stream<String> distinct = Stream.of("a"."b"."c"."d"."a"."b"."a"."c")
.distinct();
distinct.forEach(System.out::println);
// The equals and hashcode methods need to be overridden in the Student class to remove duplicate data
Stream.of(new Student("Zhang".18),
new Student("Bill".20),
new Student("Zhang".18),
new Student("Fifty".22),
new Student("Bill".20))
.distinct()
.forEach(System.out::println);
}
Copy the code
AllMatch, anyMatch, nonMatch
AllMatch (), anyMatch(), and nonMatch() methods to determine whether data matches specified conditions
//allMatch() : Whether all elements match conditions
boolean allMatch(Predicate<? super T> predicate);
//anyMatch() : Whether the element has any matching conditions
boolean anyMatch(Predicate<? super T> predicate);
//nonMatch() : Whether all elements do not meet the condition
boolean noneMatch(Predicate<? super T> predicate);
Copy the code
Use:
List<Integer> list = new ArrayList<>();
list.add(13);
list.add(12);
list.add(8);
list.add(4);
boolean b1 = list.stream().allMatch((n) -> {return n > 8; });//false
boolean b2 = list.stream().anyMatch((n) -> {return n > 8; });//true
boolean b3 = list.stream().noneMatch((n) -> {return n > 8; });//false
Copy the code
sorted
The sorted() method sorts the data in the stream
Stream<T> sorted();
Stream<T> sorted(Comparator<? super T> comparator);
@FunctionalInterface
public interface Comparator<T> {
int compare(T o1, T o2);
}
Copy the code
Use:
List<Integer> list = new ArrayList<>();
list.add(13);
list.add(12);
list.add(8);
list.add(4);
list.stream().sorted((str1,str2)->(str1-str2)).forEach(System.out::println);
Copy the code
count
Used to count the number of elements and returns a value of type long representing the number of elements
long count();
Copy the code
Use:
public static void main(String[] args) {
long count = Stream.of("a"."b"."c"."d"."a"."b"."a"."c")
.count();
System.out.println("The number of elements is:"+count);
}
Copy the code
peek
List<Person> lists = new ArrayList<Person>();
lists.add(new Person(1L, "p1"));
lists.add(new Person(2L, "p2"));
lists.add(new Person(3L, "p3"));
lists.add(new Person(4L, "p4"));
System.out.println(lists);
List<Person> list2 = lists.stream()
.filter(f -> f.getName().startsWith("p"))
.peek(t -> {
System.out.println(t.getName());
})
.collect(Collectors.toList());
System.out.println(list2);
Copy the code
mapToInt
The mapToInt() method converts elements of type Integer in a Stream to type int
IntStream mapToInt(ToIntFunction<? super T> mapper);
Copy the code
Use:
List<Integer> list = new ArrayList<>();
list.add(12);
list.add(8);
list.add(4);
list.add(13);
list.stream().mapToInt(new ToIntFunction<Integer>() {
@Override
public int applyAsInt(Integer value) {
return value;
}
}).forEach(System.out::println);
Copy the code