diff options
author | Andreas Rumpf <rumpf_a@web.de> | 2016-05-11 23:31:22 +0200 |
---|---|---|
committer | Andreas Rumpf <rumpf_a@web.de> | 2016-05-11 23:31:22 +0200 |
commit | 34110fc118a063822c74b9615ff30a2e366aa8d4 (patch) | |
tree | 489bc02ea2fd0b47a1f864ed2b00029f0358274b | |
parent | 4f9083268f2f977c72027d4f63c0186cd703b15a (diff) | |
parent | fcfe27a1f847cf8cff1b821d82c828841960f121 (diff) | |
download | Nim-34110fc118a063822c74b9615ff30a2e366aa8d4.tar.gz |
Merge pull request #4136 from oderwat/HARA-peg-replace-cb
Added a replace() with callback to pegs.
-rw-r--r-- | lib/pure/pegs.nim | 59 |
1 files changed, 59 insertions, 0 deletions
diff --git a/lib/pure/pegs.nim b/lib/pure/pegs.nim index fead66de2..b5e69595b 100644 --- a/lib/pure/pegs.nim +++ b/lib/pure/pegs.nim @@ -962,6 +962,50 @@ proc parallelReplace*(s: string, subs: varargs[ # copy the rest: add(result, substr(s, i)) +proc replace*(s: string, sub: Peg, cb: proc( + match: int, cnt: int, caps: openArray[string]): string): string {. + rtl, extern: "npegs$1cb".}= + ## Replaces `sub` in `s` by the resulting strings from the callback. + ## The callback proc receives the index of the current match (starting with 0), + ## the count of captures and an open array with the captures of each match. Examples: + ## + ## .. code-block:: nim + ## + ## proc handleMatches*(m: int, n: int, c: openArray[string]): string = + ## result = "" + ## if m > 0: + ## result.add ", " + ## result.add case n: + ## of 2: c[0].toLower & ": '" & c[1] & "'" + ## of 1: c[0].toLower & ": ''" + ## else: "" + ## + ## let s = "Var1=key1;var2=Key2; VAR3" + ## echo s.replace(peg"{\ident}('='{\ident})* ';'* \s*", handleMatches) + ## + ## Results in: + ## + ## .. code-block:: nim + ## + ## "var1: 'key1', var2: 'Key2', var3: ''" + result = "" + var i = 0 + var caps: array[0..MaxSubpatterns-1, string] + var c: Captures + var m = 0 + while i < s.len: + c.ml = 0 + var x = rawMatch(s, sub, i, c) + if x <= 0: + add(result, s[i]) + inc(i) + else: + fillMatches(s, caps, c) + add(result, cb(m, c.ml, caps)) + inc(i, x) + inc(m) + add(result, substr(s, i)) + proc transformFile*(infile, outfile: string, subs: varargs[tuple[pattern: Peg, repl: string]]) {. rtl, extern: "npegs$1".} = @@ -1789,3 +1833,18 @@ when isMainModule: assert(str.find(empty_test) == 0) assert(str.match(empty_test)) + + proc handleMatches*(m: int, n: int, c: openArray[string]): string = + result = "" + + if m > 0: + result.add ", " + + result.add case n: + of 2: c[0].toLower & ": '" & c[1] & "'" + of 1: c[0].toLower & ": ''" + else: "" + + assert("Var1=key1;var2=Key2; VAR3". + replace(peg"{\ident}('='{\ident})* ';'* \s*", + handleMatches)=="var1: 'key1', var2: 'Key2', var3: ''") |