简体   繁体   中英

how to use implicit method in trait

I am trying to understand the implicit method in Scala, in the SlashSyntax.scala I defined a customed operator method:

package com.example.hello.impl

object SlashSyntax {

  final class IntOps(private val intSrc: Int) {
    def \(a2: Int): Int = (intSrc.toString + a2.toString).toInt
  }

}

trait SlashSyntax {

  import SlashSyntax._

  implicit def intOps(src: Int) = new IntOps(src)
}

then in the main method I try to use the operator but it says cannot resolve symbol :

object Test {
  def main(args: Array[String]): Unit = {
    import com.example.hello.impl.SlashSyntax._
    val s = 10 \ 2  //cannot resolve symbol \
  }
}

How can I use my own operator?

The simplest solution is to make the IntOps class an implicit class . Then

  1. you don't need the SlashSyntax trait (or you can use it for other things)
  2. the implicit is in the right place to be imported
  3. the pesky implicit conversion method ... warning goes away

The issue caused by incorrect import.

import com.example.hello.impl.SlashSyntax._

Problem here is that you imported all members from object SlashSyntax instead of trait SlashSyntax . This happened because scala considered com.example.hello.impl.SlashSyntax as path . All paths can be composed only from Stable members . Traits are not Stable members but objects are stable members, so scala imported members from object SlashSyntax .

You can just move your implicit method to object SlashSyntax and this will fix the issue.

  1. Your object SlashSyntax doesn't extends trait SlashSyntax so your extension methods are not seen when you do SlashSyntax._ .

  2. Additionally you didn't do import scala.languageFeatures.implicitConversions . though you might have added -language:implicitConversions flag to scalac.

  3. Sometimes lack of type annotation break things. Not in your case but it's good in general to these things there.

This works:

object SlashSyntax extends SlashSyntax {

  final class IntOps(private val intSrc: Int) {
    def \(a2: Int): Int = (intSrc.toString + a2.toString).toInt
  }

}

trait SlashSyntax {

  import SlashSyntax.IntOps

  implicit def intOps(src: Int): IntOps = new IntOps(src)
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM