что не так: значение Parsers не входит в пакет scala.util.parsing.combinator?

У меня есть вышеприведенное странное сообщение об ошибке, которое я не понимаю: «значение Parsers не является членом пакета scala.util.parsing.combinator».

Я пытаюсь изучить комбинаторы Parser, шаг за шагом пишу парсер C. Я начал с токена, поэтому у меня есть классы:

import util.parsing.combinator.JavaTokenParsers
object CeeParser extends JavaTokenParsers {
    def token: Parser[CeeExpr] = ident ^^ (x => Token(x))
}

abstract class CeeExpr 
case class Token(name: String) extends CeeExpr

Это настолько просто, насколько я мог это сделать.

Приведенный ниже код работает нормально, но если я раскомментирую закомментированную строку, я получу приведенное выше сообщение об ошибке:

object Play {
  def main(args: Array[String]) {
    //val parser: _root_.scala.util.parsing.combinator.Parsers.Parser[CeeExpr] CeeParser.token
    val x = CeeParser.token
    print(x)
  }
}

Если это проблема с моей настройкой, я использую scala 2.7.6 через плагин scala для intellij. Кто-нибудь может пролить свет на это? Сообщение неверно, Parsers является членом scala.util.parsing.combinator.

--- Следовать за

Этот человек http://www.scala-lang.org/node/5475 кажется иметь ту же проблему, но я не понимаю ответа, который ему дали. Кто-нибудь может это объяснить?


person Nick Fortescue    schedule 27.03.2010    source источник


Ответы (2)


Проблема в том, что Parser является подклассом Parsers, поэтому правильным способом обращения к нему является экземпляр парсера. То есть CeeParser.Parser отличается от любого другого x.Parser.

Правильный способ обращения к типу CeeParser.tokenCeeParser.Parser.

person Daniel C. Sobral    schedule 27.03.2010

Проблема в том, что Parsers — это не пакет или класс, а трейт, поэтому его члены нельзя импортировать. Вам нужно импортировать из определенного класса, расширяющего черту.

В этом случае конкретный класс — CeeParser, поэтому тип val должен быть CeeParser.Parser[CeeExpr]:

val parser : CeeParser.Parser[CeeExpr]
person Nick Fortescue    schedule 27.03.2010
comment
Также можно обратиться к вложенному классу, используя синтаксис scala.util.parsing.combinator.Parsers#Parser[CeeExpr]. Вложенные типы в scala зависят от пути (это означает, что вложенный тип отличается для каждого экземпляра внешнего типа). Синтаксис # позволяет обойти это. - person Ben Lings; 27.03.2010
comment
Это не имеет ничего общего с чертой характера. Это дало бы ту же проблему, если бы это был класс. - person Daniel C. Sobral; 27.03.2010
comment
@ Даниэль, это правда? Я должен попробовать. Я подумал, что если бы Parser был классом, то CeeParser.Parser наверняка был бы экземпляром Parsers.Parser, так что импорт работал бы. - person Nick Fortescue; 29.03.2010
comment
Импорт CeeParser работает, импорт Parsers — нет. Класс не является ни пакетом, ни объектом. Вы не можете импортировать данные из него, только из его экземпляров. Дело не в том, что ваше решение неверно, просто класс/черта не имеют к этому никакого отношения. - person Daniel C. Sobral; 29.03.2010