scala的提取器(Extractor)

scala的提取器(Extractor)


在定义scala类的时候,如果额外自定义了unapply()方法,那么该类的对象就是一个提取器,我们就能从该对象中获取到构造该对象的值有哪些。

先来看一下没有定义unapply()方法的普通类——


(1)scala中普通类class

普通类需要通过new 操作来创建对象,每new 一个实例就创建一个全新的对象。


// 定义一个普通类

scala> class People(name:String, age:Int, city:String)

defined class People


// 通过new 操作来创建对象

scala> val cindy1 = new People("Cindy", 24, "Los Angeles")

cindy1: People = People@29394966


// cindy1和cindy2是两个不同的对象

scala> val cindy2 = new People("Cindy", 24, "Los Angeles")

cindy2: People = People@2c70a1de



再来看看定义了unapply()方法的类——


(2)携带提取器(Extractor)的类class

提取器:是一个带有unapply()方法的实例(对象)。

当我们对提取器对象使用match语句时, 会自动调用unapply()方法。


我们有时候需要使用提取器,以便从一个类的实例中获取:构造该实例的值有哪些。那么,只要把对象传递给unapply()方法,此方法就会从中提取出构造该对象的参数值。示例如下


object Customer {

    //编译器在实例化的时候,会自动调用 apply()方法

    def apply(name: String, age: Int, item: String):String = {

        name + "," + age + "," + item

    }

    /* unapply()方法是apply()的反向操作

     * 把对象传递给unapply()方法,此方法就会从中取出构造该对象的参数值。

     */

    def unapply(arg: String): Option[(String, Int, String)] = {

        val args_list = arg.split(",")

        if (args_list.length == 3) {

            Some((args_list(0), args_list(1).toInt, args_list(2)))

        }

        else None

    }

    def main(args: Array[String]) {

        //使用 apply() 方法则无需使用new 操作就能创建实例

        val obj1 = apply("Buddy", 32,"Beer")

        println("自动调用apply(),结果:\t" + obj1)

        println("调用unapply(),得到构造此对象的参数值列表:\t" + unapply(obj1))

        println("调用unapply():\t" + unapply("Goodman"))


        //编译器在实例化的时候,会自动调用 apply()方法

        val obj2 = Customer("Tony", 27,"Milk")

        println("编译器在实例化时自动调用apply(),结果: "+obj2)


        //对提取器对象 obj2 使用match语句,则自动调用unapply()

        obj2 match {

            case Customer(str) => printf("构造出对象 %s 的参数有: %s",obj2,str)

            case _ => println("nothing")

        }

    }

}


【运行 Customer 的输出结果】

自动调用apply(),结果:Buddy,32,Beer

调用unapply(),得到构造此对象的参数值列表:Some((Buddy,32,Beer))

调用unapply(): None

编译器在实例化时自动调用apply(),结果: Tony,27,Milk

构造出对象 Tony,27,Milk 的参数有: (Tony,27,Milk)



最后来看一下无需手动定义unapply()的样例类——


(3)样例类 case class

不同于普通类class ,样例类内置了apply和unapply方法,创建对象时不需要new。

通过样例类,我们可以直接通过实例调用unapply()方法获取构造该实例的值。


scala> case class User(name:String, age:Int, city:String)

defined class User


scala> User.

apply   curried   toString   tupled   unapply


// 通过 apply 方法, 无需使用 new 操作就能创建对象

scala> val tony = User.apply("tony", 27, "Peking")

tony: User = User(tony,27,Peking)


//查看由哪些值构造了此对象

scala> User.unapply(tony)

res5: Option[(String, Int, String)] = Some((tony,27,Peking))

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值