lambda高级进阶--组合函数

只有一个参数的函数可以将一个值转换成另一个值,如果你有2个这样的转换函数,那么在进行一个转换之后在进行第二个转换,其实也是一个中转换。

说到这里,先说一下我个人的一个习惯,我在写javaBean的set()方法时,一半都不是void类型,都是返回当前对象,这样子我在给这个对象设值的时候就可以一直打点调下去了,不用罗里吧嗦的写很多次对象了。

OK,现在回到主题,我们先来考虑一个情景,我们自己写一个静态方法来实现对一个字符串的处理,代码如下:
public class Linkin
{
	public static void main(String[] args)
	{
		// 操作"LinkinPark..."第一次
		String str1 = function("LinkinPark...", String::toLowerCase);
		System.out.println(str1);
		// 操作"LinkinPark..."第二次
		String str2 = function(str1, String::toUpperCase);
		System.out.println(str2);
	}


	// 模拟一个静态方法,来对str这个字符串做一元操作
	public static String function(String str, UnaryOperator<String> function)
	{
		return function.apply(str);
	}
}


上面的代码没什么问题,但是我们性能上考虑一下上面的这种编码就会发现一个坏处,就是我们在对“LinkinPark”这个字符串做了多次操作,其实我们只是需要最后一次的结果,那么在这中间我们都创建了一个中间字符串,它可能需要不小的存储空间,所以我们现在应该将这些操作都组合起来,然后将组合起来的操作一次性的应用到每个像素上,这样就好多了。看下面代码:

public class Linkin
{
	public static void main(String[] args)
	{
		// 将前面的2次操作直接合并
		String str1 = function1("LinkinPark...", String::toLowerCase, String::toUpperCase);
		System.out.println(str1);
	}


	// 模拟一个静态方法,来对str这个字符串做一元操作
	public static String function(String str, UnaryOperator<String> function1, UnaryOperator<String> function2)
	{
		return function2.apply(function1.apply(str));
	}


	// 模拟一个静态方法,不限制传入操作的个数
	public static String function1(String str, UnaryOperator<String>... function)
	{
		for (UnaryOperator<String> unaryOperator : function)
		{
			str = unaryOperator.apply(str);
		}
		return str;
	}
}

总结一下:一般来说,当我们在写一个可以被用户连续变换效果的API时,就应该能让用户组合这些效果。其实Stream也是这么建议我们用它的API来这样子编码的。
原文地址:https://www.cnblogs.com/LinkinPark/p/5232952.html