标签: scala-compiler

创建一个含糊的低优先级隐式

考虑io包装中提供的默认编解码器。

implicitly[io.Codec].name  //res0: String = UTF-8
Run Code Online (Sandbox Code Playgroud)

它是“低优先级”隐式的,因此很容易覆盖而不会产生歧义。

implicit val betterCodec: io.Codec = io.Codec("US-ASCII")

implicitly[io.Codec].name  //res1: String = US-ASCII
Run Code Online (Sandbox Code Playgroud)

提高优先级也很容易。

import io.Codec.fallbackSystemCodec
implicit val betterCodec: io.Codec = io.Codec("US-ASCII")

implicitly[io.Codec].name  //won't compile: ambiguous implicit values
Run Code Online (Sandbox Code Playgroud)

但是我们可以朝相反的方向前进吗?我们可以创建一个低级别的隐式来禁用(“歧义化”)默认值吗?我一直在研究优先级方程式,并使用低优先级隐式变量进行操作,但尚未创建默认值的歧义。

scala implicit scala-macros scala-compiler

10
推荐指数
1
解决办法
421
查看次数

How does the Scala compiler perform implicit conversion?

I have a custom class, A, and I have defined some operations within the class as follows:

def +(that: A) = ...
def -(that: A) = ...
def *(that: A) = ...

def +(that: Double) = ...
def -(that: Double) = ...
def *(that: Double) = ...
Run Code Online (Sandbox Code Playgroud)

In order to have something like 2.0 + x make sense when x is of type A, I have defined the following implicit class:

object A {
  implicit class Ops (lhs: …
Run Code Online (Sandbox Code Playgroud)

scala scalac scala-compiler scala-quasiquotes

7
推荐指数
1
解决办法
182
查看次数

将闭包传递给Scala编译器插件

我正在尝试编写一个Scala编译器插件,它允许非常通用的代码生成:类似于C预处理器的通用性,但更多类型安全(我不确定这是否是一个糟糕的想法,但它是一个有趣的练习).我理想的用例看起来像这样:

// User code. This represents some function that might take some args
// and outputs an abstract syntax tree.
def createFooTree(...): scala.reflect.runtime.universe.Tree = ...

// Later user code (maybe separate compilation?). Here the user generates
// code programmatically using the function call to |createFooTree| and inserts
// the code using insertTree.
insertTree(createFooTree(...))
Run Code Online (Sandbox Code Playgroud)

重要的插件代码可能如下所示(基于):

class InsertTreeComponent(val global: Global)
  extends PluginComponent
  with TypingTransformers {
  import global._
  import definitions._

  override val phaseName = "insertTree"

  override val runsRightAfter = Some("parser")
  override …
Run Code Online (Sandbox Code Playgroud)

scala scalac scala-compiler

6
推荐指数
1
解决办法
414
查看次数

为什么scala编译器不会在模式匹配中始终产生false的if语句生成警告?

scala编译器应该为我在下面评论过的if语句生成警告,但事实并非如此.为什么?

sealed trait T
object A extends T

val s:Seq[T] = Seq(A)

val result = s.map {
    //This if should produce a compiler warning
    case a if(a == "A") => 
        "First"
    case a => 
      //This if should produce a compiler warning
      if (a == "A") {
        "Second"
      }
      else
      {
        "Third"
      }
}
Run Code Online (Sandbox Code Playgroud)

其结果将是"第三条:"如你所期望,但是编译器应该产生一个警告就case a if(a == "A")和上if (a == "A"),但很可惜没有警告.

如果我编写以下代码,它的行为就像我期望的那样:

if(A == "A"){
  println("can't happen")
}

// warning: comparing values of types A.type and …
Run Code Online (Sandbox Code Playgroud)

scala scala-compiler

6
推荐指数
1
解决办法
180
查看次数

获取Scala中"超级"调用引用的符号

我正在为refchecks阶段编写一个Scala编译器插件.

如何访问的符号,一个"超级"的呼叫是指,考虑调用点的象征?

例如,在

trait A {
  def m() {}
}

trait B extends A {
  def m() { super.m() }
}
Run Code Online (Sandbox Code Playgroud)

知道了呼叫站点的符号super.m(),我想获得特征的符号A.

compiler-construction static-analysis scala scala-compiler

5
推荐指数
1
解决办法
93
查看次数

Scala解析器削减最后一个括号

Welcome to Scala 2.12.1 (Java HotSpot(TM) 64-Bit Server VM, Java 1.8.0_121).
Type in expressions for evaluation. Or try :help.

scala> :paste
// Entering paste mode (ctrl-D to finish)

import scala.reflect.runtime._
import scala.reflect.runtime.universe._
import scala.tools.reflect.ToolBox

val mirror = universe.runtimeMirror(universe.getClass.getClassLoader)
val toolbox = mirror.mkToolBox(options = "-Yrangepos")
val text =
  """
    |libraryDependencies ++= Seq("org.scala-lang" % "scala-compiler" % "2.10.4") map {
    |    (dependency) =>{
    |        dependency
    |    }
    |}
  """.stripMargin
val parsed = toolbox.parse(text)

val parsedTrees = parsed match {
  case Block(stmt, expr) => …
Run Code Online (Sandbox Code Playgroud)

scala scala-compiler scala-2.11 scala-reflect scala-2.12

5
推荐指数
1
解决办法
229
查看次数

如果 bound 是抽象类型成员,则具有上限类型的高级类型构造函数不起作用

我想定义一个由上限R和更高级类型构造函数参数化的特征,该构造函数F[_]仅接受R. 我希望这个 trait 实现一个多态apply,可以将 anyF[A]转换为Unit,前提是A <: R.

这段代码工作得很好:

import scala.language.higherKinds

// this is the trait with polymorphic `apply`
trait CoCone[R, F[_ <: R]] {
  def apply[A <: R](x: F[A]): Unit
}

// Example:
sealed trait Domain
class Dom1 extends Domain

class Fnctr[X <: Domain]

val c = new CoCone[Domain, Fnctr] {
  def apply[D <: Domain](x: Fnctr[D]): Unit = ()
}
Run Code Online (Sandbox Code Playgroud)

(见下面关于命名的备注)

现在,如果我通过将R它声明为某个模块的类型成员来抽象它,并Fnctr[A <: …

scala abstract-type higher-kinded-types type-bounds scala-compiler

5
推荐指数
1
解决办法
294
查看次数

为什么用模式匹配收集不能缩小特定类?

让我们考虑以下特征:

sealed trait AB
case class A(a: Int) extends AB
case class B(b: Int) extends AB
Run Code Online (Sandbox Code Playgroud)

我试图将collect集合限制为特定的子类.

如果我尝试collect,匹配单个组件并重新组合元组:

scala> Seq.empty[(Int, AB)].collect { case (id, a @ A(_))  => (id, a) } : Seq[(Int, A)]
res6: Seq[(Int, ab.A)] = List()
Run Code Online (Sandbox Code Playgroud)

编译器很高兴,但如果尝试返回完整匹配:

scala> Seq.empty[(Int, AB)].collect { case x @ (_, A(_))  => x } : Seq[(Int, A)]
Run Code Online (Sandbox Code Playgroud)

事情变得丑陋:

<console>:27: error: type mismatch;
 found   : Seq[(Int, ab.AB)]
 required: Seq[(Int, ab.A)]
       Seq.empty[(Int, AB)].collect { case x @ (_, A(_))  => …
Run Code Online (Sandbox Code Playgroud)

scala type-inference pattern-matching scala-collections scala-compiler

5
推荐指数
1
解决办法
181
查看次数

我可以检查我的 Scala 代码库以查找所有类型的警告:“比较无关类型”吗?

我想检查我的代码库以找到“无结果类型测试”警告和“比较无关类型”警告我们的代码库中基本上有一个非常大的错误,如果我们没有忽略这个警告,本可以避免的。我们现在要检查代码以查找我们的代码库中是否还有其他实例?

scala scala-compiler

5
推荐指数
1
解决办法
194
查看次数

Scala 编译错误:未找到:类型 _$1

我正在研究 Scala 中的存在类型2.12.x。为此,我正在测试以下代码:

trait Parent
class ChildA extends Parent
class ChildB extends Parent

def whatIsInside(opt: Option[_ <: Parent]): String = {
  opt match {
    case _: Option[_ <: ChildA] => "ChildA"
    case _: Option[_ <: ChildB] => "ChildB"
    case _                      => throw new IllegalArgumentException("unknown type")
  }
}


whatIsInside(Some(new ChildA))
Run Code Online (Sandbox Code Playgroud)

由于类型擦除,我不希望这在运行时起作用,但是这甚至无法编译。我收到以下错误:

[error] ExistentialTypes.scala:12:24: not found: type _$2
[error]         case _: Option[_ <: ChildA] => "ChildA"
[error]                        ^
[error] ExistentialTypes.scala:13:24: not found: type _$3
[error]         case _: Option[_ …
Run Code Online (Sandbox Code Playgroud)

scala pattern-matching existential-type scalac scala-compiler

5
推荐指数
1
解决办法
368
查看次数