1 |
|
2 |
|
3 |
|
4 |
|
5 |
|
6 | export default function balanced (a, b, str) {
|
7 | if (a instanceof RegExp) a = maybeMatch(a, str)
|
8 | if (b instanceof RegExp) b = maybeMatch(b, str)
|
9 |
|
10 | const r = range(a, b, str)
|
11 |
|
12 | return (
|
13 | r && {
|
14 | start: r[0],
|
15 | end: r[1],
|
16 | pre: str.slice(0, r[0]),
|
17 | body: str.slice(r[0] + a.length, r[1]),
|
18 | post: str.slice(r[1] + b.length)
|
19 | }
|
20 | )
|
21 | }
|
22 |
|
23 |
|
24 |
|
25 |
|
26 |
|
27 | function maybeMatch (reg, str) {
|
28 | const m = str.match(reg)
|
29 | return m ? m[0] : null
|
30 | }
|
31 |
|
32 |
|
33 |
|
34 |
|
35 |
|
36 |
|
37 | export function range (a, b, str) {
|
38 | let begs, beg, left, right, result
|
39 | let ai = str.indexOf(a)
|
40 | let bi = str.indexOf(b, ai + 1)
|
41 | let i = ai
|
42 |
|
43 | if (ai >= 0 && bi > 0) {
|
44 | if (a === b) {
|
45 | return [ai, bi]
|
46 | }
|
47 | begs = []
|
48 | left = str.length
|
49 |
|
50 | while (i >= 0 && !result) {
|
51 | if (i === ai) {
|
52 | begs.push(i)
|
53 | ai = str.indexOf(a, i + 1)
|
54 | } else if (begs.length === 1) {
|
55 | result = [begs.pop(), bi]
|
56 | } else {
|
57 | beg = begs.pop()
|
58 | if (beg < left) {
|
59 | left = beg
|
60 | right = bi
|
61 | }
|
62 |
|
63 | bi = str.indexOf(b, i + 1)
|
64 | }
|
65 |
|
66 | i = ai < bi && ai >= 0 ? ai : bi
|
67 | }
|
68 |
|
69 | if (begs.length) {
|
70 | result = [left, right]
|
71 | }
|
72 | }
|
73 |
|
74 | return result
|
75 | }
|