函数编程

购物车案例

Sku(商品对象信息)

package com.company.lambda.cart;

/**
 * 下单的商品对象信息
 */
public class Sku {
    //编号
    private Integer skuId;
    //商品名称
    private String skuName;
    //单价
    private Double skuPrice;
    //购买个数
    private Integer totalNum;
    //总价
    private Double totalPrice;
    //商品类别
    private Enum skuCategory;

    public Sku(Integer skuId, String skuName, Double skuPrice, Integer totalNum, Double totalPrice, Enum skuCategory) {
        this.skuId = skuId;
        this.skuName = skuName;
        this.skuPrice = skuPrice;
        this.totalNum = totalNum;
        this.totalPrice = totalPrice;
        this.skuCategory = skuCategory;
    }

    public Integer getSkuId() {
        return skuId;
    }

    public String getSkuName() {
        return skuName;
    }

    public Double getSkuPrice() {
        return skuPrice;
    }

    public Integer getTotalNum() {
        return totalNum;
    }

    public Double getTotalPrice() {
        return totalPrice;
    }

    public Enum getSkuCategory() {
        return skuCategory;
    }
}

SkuCategoryEnum

package com.company.lambda.cart;

/**
 * 商品类型的枚举
 */
public enum  SkuCategoryEnum {
    CLOTHING(10,"服装类"),
    ELECTRONICS(20,"数码类"),
    SPORTS(30, "运动类"),
    BOOKS(40,"图书类");

    // 商品类型编号
    private Integer code;
    // 商品类型名称
    private String name;

    SkuCategoryEnum(Integer code, String name) {
        this.code = code;
        this.name = name;
    }
}

CartService

package com.company.lambda.cart;

import java.util.ArrayList;
import java.util.List;

/**
 * 购物车服务类
 */
public class CartService {

    // 加入到购物车里面的商品信息
    private static List<Sku> cartSkuList = new ArrayList<>() {
        {
            add(new Sku(65266, "无人机", 4999.00,
                    1, 4999.00, SkuCategoryEnum.ELECTRONICS));

            add(new Sku(65212, "VR", 2999.00,
                    1, 2999.00, SkuCategoryEnum.ELECTRONICS));

            add(new Sku(65754, "浅色衬衫", 49.00,
                    3, 127.00, SkuCategoryEnum.CLOTHING));

            add(new Sku(65354, "短袖", 495.00,
                    1, 495.00, SkuCategoryEnum.CLOTHING));

            add(new Sku(65454, "长袖", 999.00,
                    3, 2997.00, SkuCategoryEnum.CLOTHING));

            add(new Sku(65898, "网球", 19.00,
                    5, 95.00, SkuCategoryEnum.SPORTS));

            add(new Sku(65242, "羽毛球", 99.00,
                    1, 99.00, SkuCategoryEnum.SPORTS));

            add(new Sku(65414, "Java核心技术", 99.00,
                    1, 99.00, SkuCategoryEnum.BOOKS));

            add(new Sku(65785, "Java编程思想", 80.00,
                    4, 320.00, SkuCategoryEnum.BOOKS));
        }
    };

    /**
     * 获取商品信息
     */
    public static List<Sku> getCartSkuList() {
        return cartSkuList;
    }
}

业务逻辑(找出购物车属于电子产品的一类)

CartService

package com.company.lambda.cart;

import java.util.ArrayList;
import java.util.List;

/**
 * 购物车服务类
 */
public class CartService {

    ...
        
    /**
     * Version 1.0
     * 找出购物车里面的所有商品
     * @param cartSkuList
     * @return
     */
    public static List<Sku> filterElectronicsSkus(List<Sku> cartSkuList) {
        List<Sku> result = new ArrayList<Sku>();
        for (Sku sku : cartSkuList) {
            //如果商品类型 等于 电子类
            if (SkuCategoryEnum.ELECTRONICS.equals(sku.getSkuCategory())) {
                result.add(sku);
            }
        }
        return result;
    }
}

JSON依赖

<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>fastjson</artifactId>
    <version>1.2.58</version>
</dependency>

Test

@Test
public void filterElectronicsSkus(){
    List<Sku> cartSkuList = CartService.getCartSkuList();

    //查找购物车中数码类产品
    List<Sku> result = CartService.filterElectronicsSkus(cartSkuList);

    // 以JSON的格式展现出来
    System.out.println(JSON.toJSONString(result,true));
}

在这里插入图片描述

根据传入商品类型参数,找出购物车中同种商品类型的商品列表

CartService/filterSkuByCategory

/**
     * Version 2.0
     * 根据传入商品类型参数,找出购物车中同种商品类型的商品列表
     * @param cartSkuList
     * @param category
     * @return
     */
public static List<Sku> filterSkuByCategory(List<Sku> cartSkuList,SkuCategoryEnum category) {
    List<Sku> result = new ArrayList<Sku>();
    for (Sku sku : cartSkuList) {
        //如果商品类型 等于 传入的商品类型
        if (category.equals(sku.getSkuCategory())) {
            result.add(sku);
        }
    }
    return result;
}

Test

@Test
public void filterSkuByCategory(){
    List<Sku> cartSkuList = CartService.getCartSkuList();

    // 查找购物车中服装类商品集合
    List<Sku> result = CartService.filterSkuByCategory(cartSkuList, SkuCategoryEnum.CLOTHING);

    System.out.println(JSON.toJSONString(result,true));
}

在这里插入图片描述

支持通过商品类型或总价来过滤商品

CartService/filterSkus

    /**
     *  Version.3.0
     * 支持通过商品类型或总价来过滤商品
     * @param cartSkuList
     * @param category
     * @param totalPrice
     * @param categoryOrPrice   -true:根据商品类型    false:根据商品总价
     * @return
     */
    public static List<Sku> filterSkus(List<Sku> cartSkuList, SkuCategoryEnum category, Double totalPrice, Boolean categoryOrPrice) {
        List<Sku> result = new ArrayList<Sku>();
        for (Sku sku : cartSkuList) {

            //如果根据商品类型判断,sku类型与输入类型比较
            //如果根据商品总价判断,sku总价与输入总价比较
            if ((categoryOrPrice && category.equals(sku.getSkuCategory()))
                    ||
                    (!categoryOrPrice && sku.getTotalPrice() > totalPrice)) {
                result.add(sku);
            }
        }
        return result;
    }

Test

    @Test
    public void filterSkus(){
        List<Sku> cartSkuList = CartService.getCartSkuList();

        // 查找购物车中总价大于60块钱的商品
        List<Sku> result = CartService.filterSkus(cartSkuList, null,660.00,false);

        System.out.println(JSON.toJSONString(result,true));

        // 查找购物车中服装类商品集合
        List<Sku> result2 = CartService.filterSkus(cartSkuList, SkuCategoryEnum.CLOTHING,null,true);

        System.out.println(JSON.toJSONString(result2,true));
    }

在这里插入图片描述

通过Predicate来定义一个判断标准进行筛选

SkuPredicate

public interface SkuPredicate {

    /**
     * 选择判断标准
     * 只有一个抽象接口
     * @param sku
     * @return
     */
    boolean test(Sku sku);
}

filterSkus

    /**
     * Version 4.0
     * 根据不同的Sku判断标准,对Sku列表进行过滤
     * @param cartSkuList
     * @param predicate - 不同的Sku判断标准策略
     * @return
     */
    public static List<Sku> filterSkus(List<Sku> cartSkuList, SkuPredicate predicate) {

        List<Sku> result = new ArrayList<Sku>();
        for (Sku sku : cartSkuList) {
            // 根据不同的Sku判断标准策略,对Sku进行判断
            if (predicate.test(sku)) {
                result.add(sku);
            }
        }
        return result;
    }

Test

    @Test
    public void filterSkus2(){
        List<Sku> cartSkuList = CartService.getCartSkuList();

        //过滤商品总价大于2000的商品
        List<Sku> result = CartService.filterSkus(cartSkuList, new SkuTotalPricePredicate());

        System.out.println(JSON.toJSONString(result,true));
    }

匿名类的使用

    @Test
    public void filterSkus3(){
        List<Sku> cartSkuList = CartService.getCartSkuList();

        //过滤商品总价大于2000的商品   使用匿名类(只使用一次)
        List<Sku> result = CartService.filterSkus(cartSkuList, new SkuPredicate() {
            @Override
            public boolean test(Sku sku) {
                return sku.getTotalPrice() > 2000;
            }
        });

        System.out.println(JSON.toJSONString(result,true));
    }

Lambda

    @Test
    public void filterSkusByLambda(){
        List<Sku> cartSkuList = CartService.getCartSkuList();

        //过滤商品总价大于2000的商品   使用Lambda表达式(只使用一次)
//        List<Sku> result = CartService.filterSkus(cartSkuList, (Sku sku) -> sku.getTotalPrice() > 2000);
        List<Sku> result = CartService.filterSkus(cartSkuList, sku -> sku.getTotalPrice() > 2000);

        System.out.println(JSON.toJSONString(result,true));
    }
  • Java8引入的函数式编程风格
  • 可以理解为一种匿名函数的代替
  • 通过行为参数化传递代码
  • (parameters) -> expression
  • (parameters) -> { statement; }
// 形式一:没有参数
() -> System.out.println(" Hello World !" );

// 形式二:只有一个参数
name -> System.out.println(" Hello World from"+ name +"!");

// 形式三:没有参数,逻辑复杂
()->{
    System.out.println(" Hello" );
    System.out.println(" World" );
}

// 形式四:包含两个参数的方法
BinaryOperator<Long> functionAdd= (x,y)-> X+ y;
Long result = functionAdd.apply(1L, 2L);

// 形式五:对参数显示声明
BinaryOperator<Long> functionAdd= (Long x, Long y)-> X+ y;
Long result = functionAdd.apply(1L, 2L);

函数式接口

  • 接口中只有一个抽象方法
  • Java8的函数式接口注解: @FunctionInterface
  • 函数式接口的抽象方法签名:函数描述符

小测试

自定义函数式接口,实现读取本地文件后自定义处理逻辑功能。

FileConsumer

/**
 * 文件处理函数式接口
 */
@FunctionalInterface
public interface FileConsumer {

    /**
     * 函数式接口抽象方法
     * @param fileContent - 文件内容字符串
     */
    void fileHander(String fileContent);
}

FileService

// 文件服务类
public class FileService {

    /**
     * 从url获取本地数据内容,调用函数式接口处理
     *
     * @param url
     * @param fileConsumer
     */
    public void fileHandle(String url, FileConsumer fileConsumer) {
        // 创建文件读取流
        try (BufferedReader bufferedReader = new BufferedReader(
                new InputStreamReader(
                        new FileInputStream(url)));){
            // 定义行变量和内容stringBuilder
            String line;
            StringBuilder stringBuilder = new StringBuilder();

            // 循环读取文件内容
            while ((line = bufferedReader.readLine()) != null) {
                stringBuilder.append(line + "\n");
            }

            // 调用函数式接口方法,将文件内容传递给lambda表达式,实现业务逻辑
            fileConsumer.fileHander(stringBuilder.toString());
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

}

Test

public class FileServiceTest {

    @Test
    public void fileHangle(){
        FileService fileService = new FileService();

        fileService.fileHandle("D:\\develop_environment\\idea_place\\newJava2\\" +
                "src\\test\\java\\com\\company\\test\\FileServiceTest.java",
                fileContent -> System.out.println(fileContent));
    }
}

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ir7IgQwz-1589118613177)(D:\笔记\java进阶笔记\Java进阶笔记.assets\image-20200510213557998.png)]

常用函数接口

在这里插入图片描述

方法引用

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值