在传统的属性过滤中,如果我们要对一个类中的属性进行过滤,直接的做法就是之间判断,当对一个类的多个属性进行过滤时,需要写很多方法,逐个去判断,这样就增加了冗余的代码数量。
final List<Use> userList = Arrays.asList( new Use( "a",1,35 ), new Use( "b",3,25 ), new Use( "c",5,56 ), new Use( "d",7,89 ), new Use( "e",8,78 ) );
/** * 过滤id */ @Test public void test01() { List<Use> list = new ArrayList <>( ); for(Use us:userList) { if(us.getId()>5) { list.add( us ); } } System.out.println(list); } /** * 过滤salter */ @Test public void test06() { List<Use> list = new ArrayList <>( ); for(Use us:userList) { if(us.getSaler()>78) { list.add( us ); } } System.out.println(list); }
对于上面的实现方式可以进行进一步优化,使用策略模式
1:优化方式一 策略模式
建立一个泛型接口,
/** * ***GOOD LUCK**** * * @Author : Wukn * @Date : 2018/6/25 */ public interface FilterUser<T> { /** * 要想对Use这个对象的属性进行过滤,可以实现这个接口。这种设计模式成为策略模式 * @param o * @return */ public Boolean checkUser(Use o); }
需要对某个属性进行过滤时,就实现这个接口
对id
/** * ***GOOD LUCK**** * * @Author : Wukn * @Date : 2018/6/ */ public class FilterUserImpl implements FilterUser<Use>{ @Override public Boolean checkUser(Use o) { return o.getId()>5?true:false; } }
对dalter
/** * ***GOOD LUCK**** * * @Author : Wukn * @Date : 2018/6/ */ public class FilterUseSaleImpl implements FilterUser<Use>{ @Override public Boolean checkUser(Use o) { return o.getSaler()>78?true:false; } }
测试方法
/** * * @param list * @param filterUser */ public void test02(List<Use> list, FilterUser<Use> filterUser) { List<Use> l = new ArrayList <>( ); for(Use user:list) { if(filterUser.checkUser( user )) { l.add( user ); } } System.out.println(l); } /** * 这样对一个类中的属性进行过滤时,可要直线接口就可以实现,降低很多垃圾代码 */ @Test public void tesd() { /** * 过滤id */ test02( userList,new FilterUserImpl() ); /** * 过滤salter */ test02( userList,new FilterUseSaleImpl() ); }
这样就完成了。
2:优化方式一 匿名内部类
对于上面策略模式实现。有一个最大的弊端就是会创建很多实现类,这样其实没必要,为了解决这样的问题的。使用匿名内部类去可以解决
/** * * @param list * @param filterUser */ public void test02(List<Use> list, FilterUser<Use> filterUser) { List<Use> l = new ArrayList <>( ); for(Use user:list) { if(filterUser.checkUser( user )) { l.add( user ); } } System.out.println(l); }
/** * 优化方式二 * 匿名内部类 * */ @Test public void test1() { test02( userList, new FilterUser <Use>( ) { @Override public Boolean checkUser(Use o) { //想要过滤那个属性就在这里直接判断,不需要再去实现多个接口 return o.getId()>5?true:false; } } ); }
3:优化方式三
对于上面的匿名内部类使用,其实有一个问题就是。多余的代码很多。。核心代码就那一行比较的,所有就产生了第三种优化
就是java8新的特性Lambda表达式。
/** * * @param list * @param filterUser */ public void test02(List<Use> list, FilterUser<Use> filterUser) { List<Use> l = new ArrayList <>( ); for(Use user:list) { if(filterUser.checkUser( user )) { l.add( user ); } } System.out.println(l); }
/** * 优化方式三 * Lambda表达式 */ public void test2() { test02( userList,(u) -> u.getId()>5?true:false ); }
优化方式四:不适应模式和匿名内部类,只有数据,可以使用java8的Stream Api
final List<Use> userList = Arrays.asList( new Use( "a",1,35 ), new Use( "b",3,25 ), new Use( "c",5,56 ), new Use( "d",7,89 ), new Use( "e",8,78 ) );
/** * 优化方式四 */ @Test public void test3() { userList.stream() .filter( (use -> use.getId()>5?true:false) ) .forEach(System.out::println); }