Java8函数式接口-Function
Java8函数式接口-Function
Function 接口常用于将一种类型的值转换为另一种类型的值 , 或对输入参数执行某种计算或处理操作。
只要理解到了这种转换关系,下面这些接口应该很容易就可以知道怎么去使用。
1. 通用 Function 接口分类
在 java.util.function
包下,共计 17 个接口。 按照功能以及参数分类。可以分成下面几个小类,这样可以更好的记忆:
1.1 基础接口
基础接口就是通过泛型实现入参跟出参,可以根据需要固化为具体的类型。
- Function
- BiFunction
1.2 基本数据类型的 Function 接口
- DoubleFunction
- IntFunction
- LongFunction
1.3 对象类型转换为基本数据类型
- ToDoubleFunction
- ToIntFunction
- ToLongFunction
1.4 两个对象类型转换为基本数据类型
- ToDoubleBiFunction
- ToIntBiFunction
- ToLongBiFunction
1.5 基本数据类型之间相互转换
- DoubleToIntFunction
- DoubleToLongFunction
- IntToDoubleFunction
- IntToLongFunction
- LongToDoubleFunction
- LongToIntFunction
2. 接口的设计思路
Function
接口的设计思路是提供一个通用的函数抽象,用于表示接收一个参数并产生一个结果的函数。使用泛型的方式,允许指定输入参数和输出结果的类型,可以灵活地应用于各种场景。
BiFunction
跟 Function
设计思路也是一样的,只不过 BiFunction
是接收两个参数然后产生一个结果的函数。
3. 通用 Function 接口定义
3.1 Function
源码:
@FunctionalInterface
public interface Function<T, R> {
R apply(T t);
default <V> Function<V, R> compose(Function<? super V, ? extends T> before) {
Objects.requireNonNull(before);
return (V v) -> apply(before.apply(v));
}
default <V> Function<T, V> andThen(Function<? super R, ? extends V> after) {
Objects.requireNonNull(after);
return (T t) -> after.apply(apply(t));
}
static <T> Function<T, T> identity() {
return t -> t;
}
}
作用:接收一个参数并返回一个结果的操作。
使用场景: 将一个对象转换为另一个类型的时候可以使用 。 比如 POJO、DTO 等对象的转换。
final Function<String, Integer> strLength = String::length;
// 结果为 5
final int length = strLength.apply("Hello");
3.2 BiFunction
源码:
@FunctionalInterface
public interface BiFunction<T, U, R> {
/**
* Applies this function to the given arguments.
*
* @param t the first function argument
* @param u the second function argument
* @return the function result
*/
R apply(T t, U u);
default <V> BiFunction<T, U, V> andThen(Function<? super R, ? extends V> after) {
Objects.requireNonNull(after);
return (T t, U u) -> after.apply(apply(t, u));
}
}
作用: 接收两个参数并返回一个结果的操作。
使用场景:将两个不同类型的对象转换为为另一种类型时使用。
final BiFunction<String, String, String> concat = String::concat;
// 结果为 "Hello World"
final String result = concat.apply("Hello", " World");
3.3 DoubleFunction
源码:
@FunctionalInterface
public interface DoubleFunction<R> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
R apply(double value);
}
作用: 接收一个 double 类型参数并返回一个结果。
使用场景: 将一个 double 类型的值转换为为另一种类型时使用。
final DoubleFunction<String> doubleToString = Double::toString;
// 结果为 "3.14"
final String result = doubleToString.apply(3.14);
3.4 IntFunction
源码:
@FunctionalInterface
public interface IntFunction<R> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
R apply(int value);
}
作用:接收一个 int 类型参数并返回一个结果。
使用场景:将一个 int 类型的值转换为另一种类型时使用。
final IntFunction<String> intToString = Integer::toString;
// 结果为 "42"
final String result = intToString.apply(42);
3.5 LongFunction
源码:
@FunctionalInterface
public interface LongFunction<R> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
R apply(long value);
}
作用:接收一个 long 类型参数并返回一个结果的操作。
使用场景:将一个 long 类型的值转换为另一种类型时使用。
final LongFunction<String> longToString = Long::toString;
// 结果为 "123"
final String result = longToString.apply(123L);
3.6 ToDoubleFunction
源码:
@FunctionalInterface
public interface ToDoubleFunction<T> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
double applyAsDouble(T value);
}
作用:接收一个参数并返回一个 double 类型结果的操作。
使用场景:将一个对象转换为 double 类型的值可以使用。
final ToDoubleFunction<String> parseDouble = Double::parseDouble;
// 结果为 3.14
final double result = parseDouble.applyAsDouble("3.14");
3.7 ToDoubleBiFunction
源码:
public interface ToDoubleBiFunction<T, U> {
/**
* Applies this function to the given arguments.
*
* @param t the first function argument
* @param u the second function argument
* @return the function result
*/
double applyAsDouble(T t, U u);
}
作用:接收两个参数并返回一个 double 类型结果的操作。
3.8 ToIntFunction
源码:
@FunctionalInterface
public interface ToIntFunction<T> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
int applyAsInt(T value);
}
使用场景:将一个对象转换为 int 类型的值的时候可以用。
final ToIntFunction<String> parseInt = Integer::parseInt;
// 结果为 42
final int result = parseInt.applyAsInt("42");
3.9 ToIntBiFunction
源码:
public interface ToIntBiFunction<T, U> {
/**
* Applies this function to the given arguments.
*
* @param t the first function argument
* @param u the second function argument
* @return the function result
*/
int applyAsInt(T t, U u);
}
作用:接收两个参数并返回一个 int 类型结果的操作。
3.10 ToLongFunction
源码:
@FunctionalInterface
public interface ToLongFunction<T> {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
long applyAsLong(T value);
}
使用场景:将一个对象转换为 long 类型的值的时候可以用。
final ToLongFunction<String> parseLong = Long::parseLong;
// 结果为 123L
final long result = parseLong.applyAsLong("123");
3.11 ToLongBiFunction
源码:
@FunctionalInterface
public interface ToLongBiFunction<T, U> {
/**
* Applies this function to the given arguments.
*
* @param t the first function argument
* @param u the second function argument
* @return the function result
*/
long applyAsLong(T t, U u);
}
作用:接收两个参数并返回一个 long 类型结果的操作。
3.12 DoubleToIntFunction
源码:
@FunctionalInterface
public interface DoubleToIntFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
int applyAsInt(double value);
}
使用场景: 将 double 类型的值转换为 int 类型的值时可以使用。
final DoubleToIntFunction doubleToInt = x -> (int) x;
// 结果为 3
final int result = doubleToInt.applyAsInt(3.14);
3.13 DoubleToLongFunction
源码:
@FunctionalInterface
public interface DoubleToLongFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
long applyAsLong(double value);
}
使用场景: 将 double 类型的值转换为 long 类型的值时可以使用。
final DoubleToLongFunction doubleToLong = x -> (long) x;
// 结果为 3L
final long result = doubleToLong.applyAsLong(3.14);
3.14 IntToDoubleFunction
源码:
@FunctionalInterface
public interface IntToDoubleFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
double applyAsDouble(int value);
}
使用场景: 将一个 int 类型的值转换为 double 类型时可以使用。
final IntToLongFunction intToLong = x -> (long) x;
// 结果为 42L
final long result = intToLong.applyAsLong(42);
3.15 IntToLongFunction
源码:
@FunctionalInterface
public interface IntToLongFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
long applyAsLong(int value);
}
使用场景: 将一个 int 类型的值转换为 long 类型时可以使用。
final IntToLongFunction intToLong = x -> (long) x;
// 结果为 42L
final long result = intToLong.applyAsLong(42);
3.16 LongToDoubleFunction
源码:
@FunctionalInterface
public interface LongToDoubleFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
double applyAsDouble(long value);
}
使用场景: 将一个 long 类型的值转换为 double 类型时可以使用。
final LongToDoubleFunction longToDouble = x -> (double) x;
// 结果为 123.0
final double result = longToDouble.applyAsDouble(123L);
3.17 LongToIntFunction
源码:
@FunctionalInterface
public interface LongToIntFunction {
/**
* Applies this function to the given argument.
*
* @param value the function argument
* @return the function result
*/
int applyAsInt(long value);
}
使用场景: 将一个 long 类型的值转换为 int 类型时可以使用。
final LongToIntFunction longToInt = x -> (int) x;
// 结果为 123
final int result = longToInt.applyAsInt(123L);
4. JDK 中使用案例
官方的案例中,大部分 Function
接口都是与 Stream API 一起使用,实现集合的流式处理。
4.1 例子 - 字符串列表转换为字符串的长度列表
这里给个使用案例,假设有一个字符串列表,然后需要获取字符串列表的长度。
使用的接口就是 Function,同时限定泛型为
import java.util.Arrays;
import java.util.List;
import java.util.function.Function;
import java.util.stream.Collectors;
public class FunctionExample {
public static void main(String[] args) {
final List<String> names = Arrays.asList("str01", "str", "string2");
// 使用 Function 接口将字符串转换为长度
final Function<String, Integer> stringLength = String::length;
final List<Integer> lengths = names.stream()
.map(stringLength)
.collect(Collectors.toList());
// 输出: [5, 3, 7]
System.out.println(lengths);
}
}
5. 实际项目运用案例
5.1 基本的 Function 来做数据转换案例
使用 Function 接口将电压值转换为功率值。
// 使用Function接口将电压值转换为功率值
fianl Function<Double, Double> function = voltage -> voltage * voltage / resistance;
final double power = voltageToPower.apply(36.0);
5.2 基本数据类型的 Function 接口转换案例
使用 IntFunction 接口计算变压器的输出电压。
final IntFunction<Integer> function = inputVoltage -> inputVoltage * 10;
final int outputVoltage = function.apply(22);
System.out.println("变压器输入电压为22伏时,输出电压为" + outputVoltage + "伏");
5.3 对象类型转换为基本数据类型案例
使用 ToDoubleFunction 接口将电表读数转换为千瓦时。
final ToDoubleFunction<String> function = function -> Double.parseDouble(reading) / 1000;
final double kWh = function.apply("1500");
System.out.println("电表读数为1500时,相当于" + kWh + "千瓦时");
5.4 两个对象类型转换为基本数据类型的BiFunction接口案例
使用 ToIntBiFunction 来计算电费。
final ToIntBiFunction<Double, Integer> moneyFunction = (kWh, hours) -> (int) (kWh * hours * 0.5);
fianl int money = moneyFunction.applyAsInt(2.5, 100);
System.out.println("在100小时内消耗2.5千瓦时的电力,电费为" + money + "元");
5.5 基本数据类型之间转换的Function接口案例
用 IntToDoubleFunction 接口将电量等级转换为实际电量值。
fianl IntToDoubleFunction function = level -> level * 95.5;
double energy = function.applyAsDouble(3);
System.out.println("电量等级为3时,实际电量值为" + energy);