• Lambda表达式序列化


    lambda表达式序列化后我们可以得到实现接口和实现方法的信息。

    public class Client {
    
     public static void main(String[] args) {
        SerializedLambda serializedLambda = resolve(User::getUsername);
        System.out.println(serializedLambda);
      }
    
      private static class User {
    
        public String getUsername() {
          return "lisi";
        }
      }
    
      /**
       * 解析 lambda 表达式
       *
       * @param func 需要解析的 lambda 对象
       * @param <T> 类型,被调用的 Function 对象的目标类型
       * @return 返回解析后的结果
       */
      private static <T> SerializedLambda resolve(SFunction<T, ?> func) {
        try {
          Method method = func.getClass().getDeclaredMethod("writeReplace");
          method.setAccessible(true);
          return (SerializedLambda) method.invoke(func);
        } catch (Exception e) {
          e.printStackTrace();
        }
        return null;
      }
    
      @FunctionalInterface
      private interface SFunction<T, R> extends Function<T, R>, Serializable {
    
      }
    }
    

    函数式接口实现Serializable ,java会帮我们序列化成SerializedLambda 对象,包含了函数式接口和实现方法的信息。

    public class Client {
    
      public static void main(String[] args) {
        String property = resolveProperty(User::getUsername);
        System.out.println(property);
      }
    
      private static class User {
    
        public String getUsername() {
          return "lisi";
        }
      }
    
      /**
       * 解析 lambda 表达式
       *
       * @param func 需要解析的 lambda 对象
       * @param <T> 类型,被调用的 Function 对象的目标类型
       * @return 返回解析后的结果
       */
      private static <T> SerializedLambda resolve(SFunction<T, ?> func) {
        try {
          Method method = func.getClass().getDeclaredMethod("writeReplace");
          method.setAccessible(true);
          return (SerializedLambda) method.invoke(func);
        } catch (Exception e) {
          e.printStackTrace();
        }
        return null;
      }
    
      /**
       * 将Lambda表达式转化为属性名称
       */
      public static <T> String resolveProperty(SFunction<T, ?> function) {
        SerializedLambda lambda = resolve(function);
        if (Objects.isNull(lambda)) {
          return "";
        }
        String methodName = lambda.getImplMethodName();
        if (methodName.startsWith("is")) {
          methodName = methodName.substring(2);
        } else {
          if (!methodName.startsWith("get") && !methodName.startsWith("set")) {
            throw new IllegalArgumentException("Error parsing property name '" + methodName
                + "'.  Didn't start with 'is', 'get' or 'set'.");
          }
          methodName = methodName.substring(3);
        }
        if (methodName.length() == 1 || (methodName.length() > 1 && !Character
            .isUpperCase(methodName.charAt(1)))) {
          methodName = methodName.substring(0, 1).toLowerCase(Locale.ENGLISH) + methodName.substring(1);
        }
        return methodName;
      }
    
      @FunctionalInterface
      private interface SFunction<T, R> extends Function<T, R>, Serializable {
    
      }
    }
    

    通过序列化数据,我们可以得到实现方法信息,如果是setter或Getter就可以获得属性信息。

  • 相关阅读:
    [转]在WEB下的客户端控件的开发应用
    [转]C#将文件保存到数据库中或者从数据库中读取文件
    [转]如何组织一个高效的开发团队
    [转]使用C#调用金诚信71x系列读卡器的DLL
    [转]统一建模语言UML轻松入门之综合实例
    [转]Web application 的压力测试 MS Web Application Stress Tool (was)
    [转]使用NUnit在.Net编程中进行单元测试
    国外著名人脸识别介绍文章
    js与as通信
    php访问mysql 封装
  • 原文地址:https://www.cnblogs.com/strongmore/p/13616705.html
Copyright © 2020-2023  润新知