Skip to content

Commit 120b42c

Browse files
committed
moar capture list
1 parent fe5f2d8 commit 120b42c

File tree

5 files changed

+17
-85
lines changed

5 files changed

+17
-85
lines changed

Sources/_RegexParser/Regex/Parse/CaptureList.swift

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
//===----------------------------------------------------------------------===//
1111

1212
public struct CaptureList {
13-
var captures: [Capture]
13+
public var captures: [Capture]
1414

1515
public init() {
1616
captures = []
@@ -23,9 +23,9 @@ public struct CaptureList {
2323

2424
extension CaptureList {
2525
public struct Capture {
26-
var name: String?
27-
var type: Any.Type?
28-
var optionalDepth: Int
26+
public var name: String?
27+
public var type: Any.Type?
28+
public var optionalDepth: Int
2929

3030
public init(
3131
name: String? = nil,
Lines changed: 11 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -1,78 +1,21 @@
11
@_implementationOnly import _RegexParser
22

3-
extension CaptureStructure {
4-
var optionalCount: Int {
5-
switch self {
6-
case .atom: return 0
7-
case .optional(let o):
8-
return 1 + o.optionalCount
9-
case .tuple:
10-
// FIXME: Separate CaptureStructure and a component
11-
fatalError("Recursive nesting")
12-
@unknown default:
13-
fatalError("Unknown default")
14-
}
15-
}
16-
17-
// FIXME: Do it all in one pass, no need for all these
18-
// intermediary arrays
3+
extension CaptureList {
194
func structuralize(
205
_ list: MECaptureList,
216
_ input: String
22-
) throws -> [StructuredCapture] {
23-
24-
func mapCap(
25-
_ cap: CaptureStructure,
26-
_ storedCap: Processor<String>._StoredCapture
27-
) -> StructuredCapture {
28-
// TODO: CaptureList perhaps should store a
29-
// metatype or relevant info...
30-
let optCount = cap.optionalCount
31-
32-
if cap.atomType.base == Substring.self {
33-
// FIXME: What if a typed capture is Substring?
34-
assert(!storedCap.hasValues)
35-
36-
if let r = storedCap.latest {
37-
return StructuredCapture(
38-
optionalCount: optCount,
39-
storedCapture: StoredCapture(range: r))
40-
}
7+
) -> [StructuredCapture] {
8+
assert(list.values.count == captures.count)
419

42-
return StructuredCapture(
43-
optionalCount: optCount,
44-
storedCapture: nil)
45-
}
10+
var result = [StructuredCapture]()
11+
for (cap, meStored) in zip(self.captures, list.values) {
12+
let stored = StoredCapture(
13+
range: meStored.latest, value: meStored.latestValue)
4614

47-
guard (storedCap.isEmpty || storedCap.hasValues) else {
48-
print(storedCap)
49-
fatalError()
50-
}
51-
// TODO: assert types are the same, under all the
52-
// optionals
53-
54-
if let v = storedCap.latestValue {
55-
return StructuredCapture(
56-
optionalCount: optCount,
57-
storedCapture: StoredCapture(range: storedCap.latest, value: v))
58-
}
59-
return StructuredCapture(
60-
optionalCount: optCount,
61-
storedCapture: nil)
62-
}
63-
64-
switch self {
65-
case let .tuple(values):
66-
assert(list.values.count == values.count)
67-
var result = Array<StructuredCapture>()
68-
for (cap, storedCap) in zip(values, list.values) {
69-
result.append(mapCap(cap, storedCap))
70-
}
71-
return result
72-
73-
default:
74-
assert(list.values.count == 1)
75-
return [mapCap(self, list.values.first!)]
15+
result.append(.init(
16+
optionalCount: cap.optionalDepth, storedCapture: stored))
7617
}
18+
return result
7719
}
7820
}
21+

Sources/_StringProcessing/Executor.swift

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,10 +40,8 @@ struct Executor {
4040
referencedCaptureOffsets: engine.program.referencedCaptureOffsets,
4141
namedCaptureOffsets: engine.program.namedCaptureOffsets)
4242

43-
let capStruct = engine.program.captureList._captureStructure(nestOptionals: true)
4443
let range = inputRange.lowerBound..<endIdx
45-
let caps = try capStruct.structuralize(
46-
capList, input)
44+
let caps = engine.program.captureList.structuralize(capList, input)
4745

4846
// FIXME: This is a workaround for not tracking (or
4947
// specially compiling) whole-match values.

Sources/_StringProcessing/Regex/DSLTree.swift

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -343,11 +343,6 @@ extension DSLTree.Node {
343343
}
344344
}
345345

346-
extension DSLTree {
347-
var captureStructure: CaptureStructure {
348-
root._captureList._captureStructure(nestOptionals: true)
349-
}
350-
}
351346
extension DSLTree.Node {
352347
/// For typed capture-producing nodes, the type produced.
353348
var valueCaptureType: AnyType? {
@@ -574,10 +569,6 @@ extension DSLTree {
574569
return abs.ast.children.map(\.dslTreeNode).map(_Tree.init)
575570
}
576571
}
577-
578-
func _captureStructure() -> CaptureStructure {
579-
self.node._captureList._captureStructure(nestOptionals: true)
580-
}
581572
}
582573

583574
@_spi(RegexBuilder)

Tests/RegexTests/CaptureTests.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -131,7 +131,7 @@ func captureTest(
131131
}
132132

133133
// Ensure DSLTree preserves literal captures
134-
let dslCapStructure = ast.dslTree.captureStructure
134+
let dslCapStructure = ast.dslTree.root._captureList._captureStructure(nestOptionals: true)
135135
guard dslCapStructure == capStructure else {
136136
XCTFail("""
137137
DSLTree did not preserve structure:

0 commit comments

Comments
 (0)