implicit final class LazyParsley[A] extends AnyRef
This class enables the prefix ~
combinator, which allows a parser in an otherwise strict
position to be made lazy.
- Source
- Parsley.scala
- Since
4.0.0
- Alphabetic
- By Inheritance
- LazyParsley
- AnyRef
- Any
- Hide All
- Show All
- Public
- Protected
Instance Constructors
Value Members
- final def !=(arg0: Any): Boolean
- Definition Classes
- AnyRef → Any
- final def ##: Int
- Definition Classes
- AnyRef → Any
- final def ==(arg0: Any): Boolean
- Definition Classes
- AnyRef → Any
- final def asInstanceOf[T0]: T0
- Definition Classes
- Any
- def clone(): AnyRef
- Attributes
- protected[lang]
- Definition Classes
- AnyRef
- Annotations
- @throws(classOf[java.lang.CloneNotSupportedException]) @native()
- final def eq(arg0: AnyRef): Boolean
- Definition Classes
- AnyRef
- def equals(arg0: AnyRef): Boolean
- Definition Classes
- AnyRef → Any
- def finalize(): Unit
- Attributes
- protected[lang]
- Definition Classes
- AnyRef
- Annotations
- @throws(classOf[java.lang.Throwable])
- final def getClass(): Class[_ <: AnyRef]
- Definition Classes
- AnyRef → Any
- Annotations
- @native()
- def hashCode(): Int
- Definition Classes
- AnyRef → Any
- Annotations
- @native()
- final def isInstanceOf[T0]: Boolean
- Definition Classes
- Any
- final def ne(arg0: AnyRef): Boolean
- Definition Classes
- AnyRef
- final def notify(): Unit
- Definition Classes
- AnyRef
- Annotations
- @native()
- final def notifyAll(): Unit
- Definition Classes
- AnyRef
- Annotations
- @native()
- final def synchronized[T0](arg0: => T0): T0
- Definition Classes
- AnyRef
- def toString(): String
- Definition Classes
- AnyRef → Any
- def unary_~: Parsley[A]
This combinator makes a parser lazy.
This combinator makes a parser lazy.
There are some combinators that are, due to Scala limitations, strict in all their parameters. Usually, a combinator is strict in its "first position", which is to say the first part of the combinator to be executed; and lazy in all other "positions". The rationale behind this is that recursion appearing in a "first position" will result in infinite recursion at parse-time, it is left-recursive after all, and so it makes little sense to waste efficiency and complicate the API to support laziness there. Since method receivers are strict and only arguments can be lazy under regular conditions, this works well.
However, for combinators that are always strict, this poses a problem: a recursion point inside one of these strict fields will cause an infinite loop at runtime! This can be fixed by ensuring that this becomes part of a lazy argument. This is a solution described by the
skip
combinator, for instance:p *> skip(q, .., r)
will ensure that theskip
is in a lazy position in*>
meaning that even if any ofq
tor
must be lazy, they can go in the strict positions of skip because thep *>
provides the required laziness. However, if this isn't possible (for instance, with thezipped
combinators), then how can this problem be solved?This is the job of the
~
combinator: very simply it wraps up a parser in a lazy box, so that even if the box is forced by a strict position, the parser will remain lazy. This means it serves as an adequate solution to this problem.- returns
the parser
p
, but guaranteed to be lazy.
// this works fine, even though all of `zipped`'s parsers are strict lazy val expr = (attempt(term) <* '+', ~expr).zipped(_ + _) <|> term // in this case, however, the following would fix the problem more elegantly: lazy val expr = (attempt(term), '+' *> expr).zipped(_ + _) <|> term
Example: - final def wait(): Unit
- Definition Classes
- AnyRef
- Annotations
- @throws(classOf[java.lang.InterruptedException])
- final def wait(arg0: Long, arg1: Int): Unit
- Definition Classes
- AnyRef
- Annotations
- @throws(classOf[java.lang.InterruptedException])
- final def wait(arg0: Long): Unit
- Definition Classes
- AnyRef
- Annotations
- @throws(classOf[java.lang.InterruptedException]) @native()