14
14
#define LLVM_ADT_STRINGSWITCH_H
15
15
16
16
#include " llvm/ADT/StringRef.h"
17
- #include " llvm/Support/Compiler.h"
18
17
#include < cassert>
19
18
#include < cstring>
20
19
#include < optional>
@@ -67,9 +66,7 @@ class StringSwitch {
67
66
68
67
// Case-sensitive case matchers
69
68
StringSwitch &Case (StringLiteral S, T Value) {
70
- if (!Result && Str == S) {
71
- Result = std::move (Value);
72
- }
69
+ CaseImpl (Value, S);
73
70
return *this ;
74
71
}
75
72
@@ -88,61 +85,59 @@ class StringSwitch {
88
85
}
89
86
90
87
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, T Value) {
91
- return Case (S0, Value). Case (S1, Value );
88
+ return CasesImpl (Value, S0, S1 );
92
89
}
93
90
94
91
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
95
92
T Value) {
96
- return Case ( S0, Value). Cases ( S1, S2, Value );
93
+ return CasesImpl (Value, S0, S1, S2);
97
94
}
98
95
99
96
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
100
97
StringLiteral S3, T Value) {
101
- return Case ( S0, Value). Cases ( S1, S2, S3, Value );
98
+ return CasesImpl (Value, S0, S1, S2, S3);
102
99
}
103
100
104
101
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
105
102
StringLiteral S3, StringLiteral S4, T Value) {
106
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, Value );
103
+ return CasesImpl (Value, S0, S1, S2, S3, S4);
107
104
}
108
105
109
106
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
110
107
StringLiteral S3, StringLiteral S4, StringLiteral S5,
111
108
T Value) {
112
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, S5, Value );
109
+ return CasesImpl (Value, S0, S1, S2, S3, S4, S5);
113
110
}
114
111
115
112
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
116
113
StringLiteral S3, StringLiteral S4, StringLiteral S5,
117
114
StringLiteral S6, T Value) {
118
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, S5, S6, Value );
115
+ return CasesImpl (Value, S0, S1, S2, S3, S4, S5, S6);
119
116
}
120
117
121
118
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
122
119
StringLiteral S3, StringLiteral S4, StringLiteral S5,
123
120
StringLiteral S6, StringLiteral S7, T Value) {
124
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, S5, S6, S7, Value );
121
+ return CasesImpl (Value, S0, S1, S2, S3, S4, S5, S6, S7);
125
122
}
126
123
127
124
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
128
125
StringLiteral S3, StringLiteral S4, StringLiteral S5,
129
126
StringLiteral S6, StringLiteral S7, StringLiteral S8,
130
127
T Value) {
131
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, S5, S6, S7, S8, Value );
128
+ return CasesImpl (Value, S0, S1, S2, S3, S4, S5, S6, S7, S8);
132
129
}
133
130
134
131
StringSwitch &Cases (StringLiteral S0, StringLiteral S1, StringLiteral S2,
135
132
StringLiteral S3, StringLiteral S4, StringLiteral S5,
136
133
StringLiteral S6, StringLiteral S7, StringLiteral S8,
137
134
StringLiteral S9, T Value) {
138
- return Case ( S0, Value). Cases ( S1, S2, S3, S4, S5, S6, S7, S8, S9, Value );
135
+ return CasesImpl (Value, S0, S1, S2, S3, S4, S5, S6, S7, S8, S9);
139
136
}
140
137
141
138
// Case-insensitive case matchers.
142
139
StringSwitch &CaseLower (StringLiteral S, T Value) {
143
- if (!Result && Str.equals_insensitive (S))
144
- Result = std::move (Value);
145
-
140
+ CaseLowerImpl (Value, S);
146
141
return *this ;
147
142
}
148
143
@@ -161,22 +156,22 @@ class StringSwitch {
161
156
}
162
157
163
158
StringSwitch &CasesLower (StringLiteral S0, StringLiteral S1, T Value) {
164
- return CaseLower (S0, Value). CaseLower (S1, Value );
159
+ return CasesLowerImpl (Value, S0, S1 );
165
160
}
166
161
167
162
StringSwitch &CasesLower (StringLiteral S0, StringLiteral S1, StringLiteral S2,
168
163
T Value) {
169
- return CaseLower ( S0, Value). CasesLower ( S1, S2, Value );
164
+ return CasesLowerImpl (Value, S0, S1, S2);
170
165
}
171
166
172
167
StringSwitch &CasesLower (StringLiteral S0, StringLiteral S1, StringLiteral S2,
173
168
StringLiteral S3, T Value) {
174
- return CaseLower ( S0, Value). CasesLower ( S1, S2, S3, Value );
169
+ return CasesLowerImpl (Value, S0, S1, S2, S3);
175
170
}
176
171
177
172
StringSwitch &CasesLower (StringLiteral S0, StringLiteral S1, StringLiteral S2,
178
173
StringLiteral S3, StringLiteral S4, T Value) {
179
- return CaseLower ( S0, Value). CasesLower ( S1, S2, S3, S4, Value );
174
+ return CasesLowerImpl (Value, S0, S1, S2, S3, S4);
180
175
}
181
176
182
177
[[nodiscard]] R Default (T Value) {
@@ -189,6 +184,39 @@ class StringSwitch {
189
184
assert (Result && " Fell off the end of a string-switch" );
190
185
return std::move (*Result);
191
186
}
187
+
188
+ private:
189
+ // Returns true when `Str` matches the `S` argument, and stores the result.
190
+ bool CaseImpl (T &Value, StringLiteral S) {
191
+ if (!Result && Str == S) {
192
+ Result = std::move (Value);
193
+ return true ;
194
+ }
195
+ return false ;
196
+ }
197
+
198
+ // Returns true when `Str` matches the `S` argument (case-insensitive), and
199
+ // stores the result.
200
+ bool CaseLowerImpl (T &Value, StringLiteral S) {
201
+ if (!Result && Str.equals_insensitive (S)) {
202
+ Result = std::move (Value);
203
+ return true ;
204
+ }
205
+ return false ;
206
+ }
207
+
208
+ template <typename ... Args> StringSwitch &CasesImpl (T &Value, Args... Cases) {
209
+ // Stop matching after the string is found.
210
+ (... || CaseImpl (Value, Cases));
211
+ return *this ;
212
+ }
213
+
214
+ template <typename ... Args>
215
+ StringSwitch &CasesLowerImpl (T &Value, Args... Cases) {
216
+ // Stop matching after the string is found.
217
+ (... || CaseLowerImpl (Value, Cases));
218
+ return *this ;
219
+ }
192
220
};
193
221
194
222
} // end namespace llvm
0 commit comments