我对Scala编程颇为陌生。除了Scala之外,我从来没有学过函数式编程。这就是说,我目前正在试图找出一个很好的方法来在使用光滑的项目上定义特征,类等。在父特征上使用泛型TableQuery类型
我的想法是有一个特性,在子类上实现方法,有些会在父类本身上实现。我找到了一种方法,但我不知道为什么。不知道这个问题与Slick或Scala的工作方式有关。
我使用的是建筑,如:
trait CompanyDAO extends BaseDao[Company]{
self: DBProfile =>
但是,这给下面的类型不匹配错误:
[error] found : slick.lifted.TableQuery[CompanyDAO.this.CompanyTable] [error] required: slick.lifted.TableQuery[CompanyDAO.this.profile.api.Table[Company]] [error] (which expands to) slick.lifted.TableQuery[CompanyDAO.this.profile.Table[Company]] [error] Note: CompanyDAO.this.CompanyTable <: CompanyDAO.this.profile.api.Table[Company], but class TableQuery is invariant in type E. [error] You may wish to define E as +E instead. (SLS 4.5) [error] override def toTable = TableQuery[CompanyTable]
但是,如果我用
self: DBProfile with BaseDao[Company] =>
然后汇编作品(顺便说一句,从another post得到解决方案)
所以,我的问题:
1)为什么使用自我类型toTable分配工作,而扩大特质不? scala如何在两种情况下解释toTable的类型?
2)有没有一种方法来适应“特性CompanyDAO扩展BaseDao”来解决错误?
预先感谢您。
import scala.concurrent.Future
import slick.basic.DatabaseConfig
import slick.jdbc.JdbcProfile
trait DBConfiguration {
lazy val config = DatabaseConfig.forConfig[JdbcProfile]("mytrade")
}
trait DBProfile {
val config: DatabaseConfig[JdbcProfile]
val db: JdbcProfile#Backend#Database = config.db
val profile : JdbcProfile = config.profile
}
trait BaseDao[T <: Any] {
self: DBProfile =>
import profile.api._
import slick.lifted.TableQuery
def toTable():TableQuery[Table[T]]
def findAll():Future[Seq[T]] = db.run(toTable.result)
}
case class Company(name: String, code: Int)
// If I use the construction like the comment below, it will fail
//trait CompanyDAO extends BaseDao[Company]{
//self: DBProfile =>
trait CompanyDAO {
self: DBProfile with BaseDao[Company] =>
//import from DBProfile trait
import profile.api._
class CompanyTable(tag: Tag) extends Table[Company](tag, "COMPANY") {
import slick.ast.BaseTypedType
import slick.jdbc.JdbcType
def name = column[String]("name")
def code = column[Int]("code")
def * = (name, code) <> (Company.tupled, Company.unapply)
}
override def toTable = TableQuery[CompanyTable]
}
编辑:一些其他的事情,我一直在努力
扩展BaseDao,如果我改变的toTable的声明:
def toTable[S <: TableQuery[Table[_]]]():S
类型不匹配会消失,但我现在收到:
test.scala:27: dead code following this construct [error] def findAll():Future[Seq[T]] = db.run(toTable.result)
试过还用自我型a nd它给了我同样的错误。
1)https:// stackoverflow。com/questions/2224932 /特质差异 - 继承和自我类型注释 2)https://stackoverflow.com/questions/1990948/what-is-the-difference-between-self-types-和特质子类 3)https://softwareengineering.stackexchange.com/questions/219038/what-is-the-difference-between-self-types-and-trait-inheritance-in-scala –