Skip to content

get rid of usages of codepoints functions that are slow #43

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
[![Dependency status](https://img.shields.io/librariesio/github/purescript-contrib/purescript-string-parsers.svg)](https://libraries.io/github/purescript-contrib/purescript-string-parsers)
[![Maintainer: paf31](https://img.shields.io/badge/maintainer-paf31-lightgrey.svg)](http://github.com/paf31)

A parsing library for parsing strings.
A parsing library for parsing strings using [Code Units](https://pursuit.purescript.org/packages/purescript-strings/docs/Data.String.CodeUnits) (JS Strings). Does not handle [Code Points](https://pursuit.purescript.org/packages/purescript-strings/docs/Data.String.CodePoints).

This library is a simpler, faster alternative to `purescript-parsing`, for when you know your input will be a string.

Expand Down
13 changes: 7 additions & 6 deletions src/Text/Parsing/StringParser/String.purs
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,9 @@ import Data.Char (toCharCode)
import Data.Either (Either(..))
import Data.Foldable (class Foldable, foldMap, elem, notElem)
import Data.Maybe (Maybe(..))
import Data.String (Pattern(..), drop, length, indexOf', stripPrefix)
import Data.String.CodeUnits (charAt, singleton)
import Data.String.CodeUnits as SCU
import Data.String.Pattern (Pattern(..))
import Data.String.Regex as Regex
import Data.String.Regex.Flags (noFlags)
import Text.Parsing.StringParser (Parser(..), ParseError(..), try, fail)
Expand All @@ -38,7 +39,7 @@ import Text.Parsing.StringParser.Combinators (many, (<?>))
eof :: Parser Unit
eof = Parser \s ->
case s of
{ str, pos } | pos < length str -> Left { pos, error: ParseError "Expected EOF" }
{ str, pos } | pos < SCU.length str -> Left { pos, error: ParseError "Expected EOF" }
_ -> Right { result: unit, suffix: s }

-- | Match any character.
Expand All @@ -60,7 +61,7 @@ anyDigit = try do
string :: String -> Parser String
string nt = Parser \s ->
case s of
{ str, pos } | indexOf' (Pattern nt) pos str == Just pos -> Right { result: nt, suffix: { str, pos: pos + length nt } }
{ str, pos } | SCU.indexOf' (Pattern nt) pos str == Just pos -> Right { result: nt, suffix: { str, pos: pos + SCU.length nt } }
{ pos } -> Left { pos, error: ParseError ("Expected '" <> nt <> "'.") }

-- | Match a character satisfying the given predicate.
Expand Down Expand Up @@ -128,7 +129,7 @@ regex pat =
where
-- ensure the pattern only matches the current position in the parse
pattern =
case stripPrefix (Pattern "^") pat of
case SCU.stripPrefix (Pattern "^") pat of
Nothing ->
"^" <> pat
_ ->
Expand All @@ -137,10 +138,10 @@ regex pat =
matchRegex r =
Parser \{ str, pos } ->
let
remainder = drop pos str
remainder = SCU.drop pos str
in
case NEA.head <$> Regex.match r remainder of
Just (Just matched) ->
Right { result: matched, suffix: { str, pos: pos + length matched } }
Right { result: matched, suffix: { str, pos: pos + SCU.length matched } }
_ ->
Left { pos, error: ParseError "no match" }
6 changes: 3 additions & 3 deletions test/Main.purs
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ import Data.List (List(Nil), (:))
import Data.List.Lazy (take, repeat)
import Data.List.NonEmpty (NonEmptyList(..))
import Data.NonEmpty ((:|))
import Data.String (joinWith)
import Data.String.CodeUnits (singleton)
import Data.String.Common as SC
import Data.Unfoldable (replicate)
import Effect (Effect)
import Test.Assert (assert', assert)
Expand Down Expand Up @@ -66,11 +66,11 @@ expectResult res p input = runParser p input == Right res

main :: Effect Unit
main = do
assert' "many should not blow the stack" $ canParse (many (string "a")) (joinWith "" $ replicate 100000 "a")
assert' "many should not blow the stack" $ canParse (many (string "a")) (SC.joinWith "" $ replicate 100000 "a")
assert' "many failing after" $ parseFail (do
as <- many (string "a")
eof
pure as) (joinWith "" (replicate 100000 "a") <> "b" )
pure as) (SC.joinWith "" (replicate 100000 "a") <> "b" )

assert $ expectResult 3 nested "(((a)))"
assert $ expectResult ("a":"a":"a":Nil) (many (string "a")) "aaa"
Expand Down