Skip to content

Remove usages of cons #5

@chriseidhof

Description

@chriseidhof

When we use a lot of cons (e.g. in many) this will slow down the code, because a copy of the array has to be made and inserting at index 0 is O(n).

There are a couple of workarounds. The most "brute-force" one would be to rewrite many (and other combinators). I'm sorry, the code is quite ugly, but I think many parts can be factored out nicely to keep everything in a functional style. The key trick is to have one result array that's not shared, so the compiler can modify it without making copies.

public func many<In, Out, Outs: RangeReplaceableCollectionType where Outs.Generator.Element == Out>(p: Parser<In, Out>) -> Parser<In, Outs>
{
    return Parser { input in
        var result = Outs()
        var remainder = input
        while true {
            switch parse(p, remainder) {
            case .Done(let input, let out):
                result.append(out)
                remainder = input
            case .Fail(_, _, _): return .Done(remainder, result)
            }
        }
    }
}

This makes it twice as fast on my machine! I think some other cases are manyTill, sepBy1, count, etc.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions