...
1 package syntax
2
3 import (
4 "bytes"
5 "errors"
6 )
7
8 type ReplacerData struct {
9 Rep string
10 Strings []string
11 Rules []int
12 }
13
14 const (
15 replaceSpecials = 4
16 replaceLeftPortion = -1
17 replaceRightPortion = -2
18 replaceLastGroup = -3
19 replaceWholeString = -4
20 )
21
22
23 var ErrReplacementError = errors.New("Replacement pattern error.")
24
25
26
27 func NewReplacerData(rep string, caps map[int]int, capsize int, capnames map[string]int, op RegexOptions) (*ReplacerData, error) {
28 p := parser{
29 options: op,
30 caps: caps,
31 capsize: capsize,
32 capnames: capnames,
33 }
34 p.setPattern(rep)
35 concat, err := p.scanReplacement()
36 if err != nil {
37 return nil, err
38 }
39
40 if concat.t != ntConcatenate {
41 panic(ErrReplacementError)
42 }
43
44 sb := &bytes.Buffer{}
45 var (
46 strings []string
47 rules []int
48 )
49
50 for _, child := range concat.children {
51 switch child.t {
52 case ntMulti:
53 child.writeStrToBuf(sb)
54
55 case ntOne:
56 sb.WriteRune(child.ch)
57
58 case ntRef:
59 if sb.Len() > 0 {
60 rules = append(rules, len(strings))
61 strings = append(strings, sb.String())
62 sb.Reset()
63 }
64 slot := child.m
65
66 if len(caps) > 0 && slot >= 0 {
67 slot = caps[slot]
68 }
69
70 rules = append(rules, -replaceSpecials-1-slot)
71
72 default:
73 panic(ErrReplacementError)
74 }
75 }
76
77 if sb.Len() > 0 {
78 rules = append(rules, len(strings))
79 strings = append(strings, sb.String())
80 }
81
82 return &ReplacerData{
83 Rep: rep,
84 Strings: strings,
85 Rules: rules,
86 }, nil
87 }
88
View as plain text