Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Repo info
Activity
    Christopher Davenport
    @ChristopherDavenport
    I’ve got everything working all the way up to combinators now. :sweat_smile:
    Rob Norris
    @tpolecat
    :-)
    Soren
    @srnb_gitlab
    This is probably asked a lot but I noticed atto-fs2 allows me to stream a String into a parser
    So I was wondering
    I want to get a Stream[F, Expr] out, i.e. parse expression by expression
    But often at times I'll have expressions that have sub-expressions
    I was wondering if I could lazily parse those sub-expressions?
    I was taking a look over your scalebythebay talk about functional programming with fixed point types
    And I feel like this is similar
    Where in that, ProfF definitely had sub-IDs that you referenced later, Expr maybe has sub-exprs that I want to get later
    trait Expr
    case class FunctionF[F[_]](name: String, subExprs: Stream[F, Expr])
    case class Function(name: String, subExprs: Vector[Expr]) extends Expr
    I'm wondering how feasible something like this is? I'm recalling your ProfF example from memory and changing it to Stream and Vector, but I may have gotten something else wrong
    Soren
    @srnb_gitlab
    Now, there's other Exprs than Function, and I'm also not sure I ever want to concretely keep a Vector[Expr]
    Soren
    @srnb_gitlab
    How do I make a parser not consume (lookAhead)? I.e. string("//") ~> manyUntil(anyChar, lineTerminator.lookAhead) for a comment?
    Alex Antonov
    @antonoal
    Hi. Is that right that when I've got Done("some non-empty string", ...) and I call .either on it I'm getting Right rather than Left with the input that couldn't hasn't been parsed?
    Rob Norris
    @tpolecat
    Leftover input is ok. If you want to disallow it you can say p <~ endOfInput which will then fail if there's anything left over.
    Alex Antonov
    @antonoal
    ok, will give it a try
    thanks!
    Rob Norris
    @tpolecat
    Or phrase(p) if you prefer.
    Bartosz Szmit
    @bszmit

    Hi ;)
    Is it possible to implement arithmetic grammar WITH substitution and division in atto?
    Grammar like this one (I know it's left recursive)

    <Exp> ::= <Exp> + <Term> | <Exp> - <Term> | <Term>
    <Term> ::= <Term> * <Factor> | <Term> / <Factor> | <Factor>
    <Factor> ::= int | ( <Exp> )

    So far I have only seen grammars without substitution and division. They require left-associativity and I guess it's a reason they are often left out in examples.

    Rob Norris
    @tpolecat
    No, not in that form. Recursive grammars end up being tricky.
    Partly because they're just tricky, partly because atto is derived from Haskell code so it's stricter than it should be in some places, partly because of bugs.
    Rob Norris
    @tpolecat
    A pattern that works iirc is, expr = listof(addend + addened) and then addend = listof(factor * factor) and factor = int | (expr). So it only recurses in the rightmost position. It's been a while, sorry. There should really be an example.
    Bartosz Szmit
    @bszmit
    I think this pattern will work for me. Thank you very much :)
    Rob Norris
    @tpolecat
    Good luck. It's treacherous. Make sure they're all lazy vals because they'll reference each other.
    jportway
    @jportway
    Hi - this is proba bly a stupid question, but i can't find an example anywhere - is there a way to match all text until something that matches another parser is encountered? I have to decode something like this:
    BLAH BLAH This is some 42 text 123\n
    I need to extract it like this:
    [BLAH][BLAH][This is some 42 text][123]
    I can extract the BLAHs easily, and I can write a parser that will match the number at the end :[whitespace number \n] but I don't know how to extract the text in between because I can only delimit that lazily - after I have found the number token at the end. This seems like it should be easy, but I can't find any documentation anywhere on how to do it.
    Rob Norris
    @tpolecat
    Hm, yeah it's not going to backtrack that way.
    jportway
    @jportway
    this seems like it must be a very common case - i'm really surprised there isn't a way to deal with it
    is this where i'd use some kind of recursive parser? I can't find any documentation about how to do that, or what it would be for...
    Rob Norris
    @tpolecat
    You could do (stringOf(elem(!_.isDigit)).token ~ int.token).many1 and then post-process the result into (String, Int). Not great.
    jportway
    @jportway
    ok - so it seems like Atto just isn't intended to do this kind of thing then? It looks like i might save some pain by just trying to stop forcing it into doing something it's not supposed to. Thanks for your help
    Rob Norris
    @tpolecat
    It's an old port of a Haskell library and I admit I have had to figure out its behavior on the fly.
    jportway
    @jportway
    :)
    the manyUntil parser seems to almost do the trick, but it discards results of the delimiting parser. I might try hacking at it a bit
    Rob Norris
    @tpolecat
    In principle you want parsers to emit every possible parse, but in practice that's really inefficient. So you end up with various compromises.
    Joseph Hajduk
    @josephhajduk
    Thanks for the awsome library. Is there a nicer way to do parser.filter(k => Try(k.toInt).isSuccess).map(_.toInt) ?
    Rob Norris
    @tpolecat
    You could use the int parser?
    Joseph Hajduk
    @josephhajduk
    I mean for the general case where you can have an exception in your map, and want the parser to roll back rather then throw the exception.
    Rob Norris
    @tpolecat
    I would use flatMap there I think.
    Salvador Fandiño
    @salva
    Hi, I am writting a parser for file system glob expressions, the code is here: https://github.com/salva/scala-glob/blob/master/src/main/scala/com/github/salva/scala/glob/GlobParser.scala
    The issue I am facing is that when I try to parse an string with it, it throws a stack overflow exception
    The parser is recursive because it has to handle nested curly brackets
    Salvador Fandiño
    @salva
    Any idea about what I am doing wrong?
    Paul Snively
    @paul-snively
    Turning an HList of Parsers and a function whose arguments are of the Parsers' types into a function taking a String to an Either of Throwable or the function's result type:
    
    import cats._, implicits._                // Be very Cats-centric
    import cats.sequence._
    
    import shapeless.{ HList, HNil }          // Only what we need from Shapeless
    import shapeless.ops.function.FnToProduct
    import shapeless.ops.hlist.IsHCons
    import shapeless.UnaryTCConstraint._
    
    import atto._, Atto._
    
    object command {
      implicit class Command[P <: HList : IsHCons : *->*[Parser]#λ](parsers: P) {
        def command[InF, InL <: HList, R](f: InF)
          (implicit
            fntop: FnToProduct.Aux[InF, InL => R],
            seq:   Sequencer.Aux[P, Parser, InL]
          ): String => Either[Throwable, R] = { s =>
            val parser = parsers.sequence
            val args   = parser.parseOnly(s).either.leftMap(s => new RuntimeException(s))
            args.map(a => fntop(f)(a))
          }
      }
    
      def describe(name: String, age: Int, height: Double) = {
        println(s"name: $name")
        println(s"age: $age")
        println(s"height: $height")
        42
      }
    
      val descCommand = (token(stringOf1(letter)) :: token(int) :: token(double) :: HNil).command(describe _)
    
      def main(args: Array[String]): Unit = descCommand("Paul 55 6.25").fold(_ => (), _ => ())
    }
    Thanks to Atto and Kittens.
    @salva: That gives me a 404.
    Rob Norris
    @tpolecat
    neato :-)
    Paul Snively
    @paul-snively
    I hadn’t encountered FnToProduct before. Kinda blows my mind that we can say “I’d like the argument list and result type of an arbitrary function, please.”
    And Kittens gives us Cats typeclasses for HList. Bam!
    “It has been 0 days since the answer was traverse/sequence.”