scala类对象null值检测并填充

本文介绍了一个Scala函数checkAndFillNull,该函数用于检查输入对象的字段是否为null,并根据字段类型用默认值进行填充,如Int字段用0,String字段用空字符串,Option[_]用None。
摘要由CSDN通过智能技术生成

scala类对象null值检测并填充

  • 这段代码是一个名为 checkAndFillNull 的 Scala 函数,它接受一个类型为 T 的对象作为输入,并返回相同类型的对象。该函数检查输入对象中的任何字段是否为 null,如果是,则根据其类型使用默认值填充它们
  • 例如,如果字段的类型为 Int,则会用 0 填充。如果字段的类型为 String,则会用空字符串(“”)填充。如果字段的类型为 Option[_],则会用 None 填充。如果字段的类型未在函数中指定,则会用 null 填充。

1. 函数实现


  
  import scala.reflect.ClassTag
  import scala.reflect.runtime.universe._

  def checkAndFillNull[T: TypeTag : ClassTag](obj: T): T = {
    // 获取输入对象的运行时的镜像
    val mirror = runtimeMirror((obj.getClass.getClassLoader))
    // 获取类符号
    val classSymbol = typeOf[T].typeSymbol.asClass
     // 获取类镜像
    val classMirror = mirror.reflectClass(classSymbol)
    // 获取构造函数符号
    val constuctorSymbol = typeOf[T].decl(termNames.CONSTRUCTOR).asMethod
    // 获取构造函数符号并反射构造函数镜像
    val constructorMirror = classMirror.reflectConstructor(constuctorSymbol)
    // 遍历构造函数符号的参数列表
    val args = constuctorSymbol.paramLists.flatten.map {
          // 对于每个参数
      param =>
//        获取参数名称
        val paramName = param.name.toString
//        获取getter方法符号
        val getterMethodSymbol = typeOf[T].decl(TermName(paramName)).asMethod
        // 反射getter方法镜像
        val getterMethodMirror = mirror.reflect(obj).reflectMethod(getterMethodSymbol)
        // 使用getter方法镜像获取字段值
        val value = getterMethodMirror.apply()
        // 如果字段值位null, 则根据字段类型使用匹配表达式确定默认值
        if (value == null) {
          val default = param.typeSignature match {
            case t if t =:= typeOf[Boolean] => false
            case t if t =:= typeOf[Char] => '\u0000'
            case t if t =:= typeOf[Byte] => 0.toByte
            case t if t =:= typeOf[Short] => 0.toShort
            case t if t =:= typeOf[Int] => 0
            case t if t =:= typeOf[Long] => 0L
            case t if t =:= typeOf[Double] => 0.0
            case t if t =:= typeOf[Float] => 0.0f
            case t if t <:< typeOf[String] => "default"
            case t if t <:< typeOf[Option[_]] => None
            case _ => None
          }
          // 将默认值转换为Object类型,添加到参数列表中
          default.asInstanceOf[Object]
        } else {
          value.asInstanceOf[Object]
        }

    }
    // 使用构造函数镜像和参数列表创建新对象并返回
    constructorMirror(args: _*).asInstanceOf[T]
  }

2. 测试用例


val testObj = TestClass(1, null, null, true, 'a', 1, 1, 1L, 1.0, 1.0f)
print(result)
assert(result.a == 1)
assert(result.b == "default")
assert(result.c == None)
assert(result.d == true)
assert(result.e == 'a')
assert(result.f == 1)
assert(result.g == 1)
assert(result.h == 1L)
assert(result.i == 1.0)
assert(result.j == 1.0f)



3. 输出效果

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值