1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
|
// cppawk: C preprocessor wrapper around awk
// Copyright 2022 Kaz Kylheku <kaz@kylheku.com>
//
// BSD-2 License
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
// 1. Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// 2. Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
// POSSIBILITY OF SUCH DAMAGE.
#ifndef __CPPAWK_ITER_H
#define __CPPAWK_ITER_H
#ifndef __CPPAWK_ITER_PRIV_H
#include "iter-priv.h"
#endif
#ifndef __CPPAWK_BASE_H
#include "base.h"
#endif
#ifndef __CPPAWK_NARG_PRIV_H
#include "narg-priv.h"
#endif
#ifndef __CPPAWK_CONS_PRIV_H
#include "cons-priv.h"
#endif
#define doarray(key, value, arr) __doarray(key, value, arr)
#define dostring(index, chr, str) __dostring(index, chr, str)
#define dofields(index, val) __dofields(index, val)
#define loop(...) __loop_temp(__VA_ARGS__) \
for (__loop_init(__VA_ARGS__); \
(__loop_test(__VA_ARGS__) || \
__loop_fini(__VA_ARGS__)) && \
__loop_prep(__VA_ARGS__); \
__loop_step(__VA_ARGS__))
#if __have_let
#define __loop_temp(...) __let(__varexpand(__temp_first, __temp_next, \
__VA_ARGS__))
#else
#define __loop_temp(...)
#endif
#define __loop_init(...) __prog(__varexpand(__init_first, __init_next, \
__VA_ARGS__))
#define __loop_test(...) __nd(__varexpand(__test_first, __test_next, \
__VA_ARGS__))
#define __loop_prep(...) __prog(__varexpand(__prep_first, __prep_next, \
__VA_ARGS__))
#define __loop_fini(...) __prog(__varexpand(__fini_first, __fini_next, \
__VA_ARGS__)) && 0
#define __loop_step(...) __prog(__varexpand(__step_first, __step_next, \
__VA_ARGS__))
#define __nd(...) __varexpand(__nd_first, __nd_next, __VA_ARGS__)
#define __nd_first(x) (x)
#define __nd_next(p, x) p && (x)
#define loop_nest(...) __varexpand2(__cross_first, __cross_next, __VA_ARGS__)
#define __cross_first(args) for (__init_ ## args; \
((__test_ ## args) || \
(__fini_ ## args) && 0) && \
__prep_ ## args; \
__step_ ## args)
#define __cross_next(prev, args) prev __cross_first(args)
#define __temp_first(args) __temp_ ## args
#define __temp_next(prev, args) prev __temp_ ## args
#define __init_first(args) __init_ ## args
#define __init_next(prev, args) prev, __init_ ## args
#define __test_first(args) __test_ ## args
#define __test_next(prev, args) prev, __test_ ## args
#define __prep_first(args) __prep_ ## args
#define __prep_next(prev, args) prev, __prep_ ## args
#define __fini_first(args) __fini_ ## args
#define __fini_next(prev, args) prev, __fini_ ## args
#define __step_first(args) __step_ ## args
#define __step_next(prev, args) prev, __step_ ## args
#define __str_s __g(ch)
#define __str_len __g(idx)
#define __temp_str(idx, ch, str) __str_s, __str_len,
#define __init_str(idx, ch, str) __str_s = (str), __str_len = length(__str_s), idx = 1
#define __test_str(idx, ch, str) idx <= __str_len
#define __prep_str(idx, ch, str) ch = substr(__str_s, idx, 1)
#define __fini_str(idx, ch, str) 1
#define __step_str(idx, ch, str) idx++
#define __temp_range(idx, from, to)
#define __init_range(idx, from, to) idx = (from)
#define __test_range(idx, from, to) idx <= (to)
#define __prep_range(idx, from, to) 1
#define __fini_range(idx, from, to) 1
#define __step_range(idx, from, to) idx++
#define __temp_range_step(idx, from, to, step)
#define __init_range_step(idx, from, to, step) idx = (from)
#define __test_range_step(idx, from, to, step) idx <= (to)
#define __prep_range_step(idx, from, to, step) 1
#define __fini_range_step(idx, from, to, step) 1
#define __step_range_step(idx, from, to, step) idx += (step)
#define __temp_from(idx, from)
#define __init_from(idx, from) idx = (from)
#define __test_from(idx, from) 1
#define __prep_from(idx, from) 1
#define __fini_from(idx, from) 1
#define __step_from(idx, from) idx++
#define __temp_from_step(idx, from, step)
#define __init_from_step(idx, from, step) idx = (from)
#define __test_from_step(idx, from, step) 1
#define __prep_from_step(idx, from, step) 1
#define __fini_from_step(idx, from, step) 1
#define __step_from_step(idx, from, step) idx += (step)
#define __temp_first_then(var, first, then)
#define __init_first_then(var, first, then) (var = (first))
#define __test_first_then(var, first, then) 1
#define __prep_first_then(var, first, then) 1
#define __fini_first_then(var, first, then) 1
#define __step_first_then(var, first, then) (var = (then))
#define for_var(var, expr) first_then(var, expr, expr)
#define __temp_list(iter, var, list)
#define __init_list(iter, var, list) iter = (list)
#define __test_list(iter, var, list) !__endp(iter)
#define __prep_list(iter, var, list) var = __car(iter)
#define __fini_list(iter, var, list) 0
#define __step_list(iter, var, list) iter = __cdr(iter)
#define __temp___list(iter, var, list)
#define __init___list(iter, var, list) iter = (list)
#define __test___list(iter, var, list) !__endp(iter)
#define __prep___list(iter, var, list) var = __car(iter)
#define __fini___list(iter, var, list) 0
#define __step___list(iter, var, list) iter = __cdr(iter)
#define __temp_fields(var) __g(var),
#define __init_fields(var) __g(var) = 1
#define __test_fields(var) __g(var) <= NF
#define __prep_fields(var) var = $ __g(var)
#define __fini_fields(var) 1
#define __step_fields(var) __g(var)++
#define __temp___fields(var) __g(var),
#define __init___fields(var) __g(var) = 1
#define __test___fields(var) __g(var) <= NF
#define __prep___fields(var) var = $ __g(var)
#define __fini___fields(var) 1
#define __step___fields(var) __g(var)++
#define __temp_keys(key, array) __g(key),
#define __init_keys(key, array) __g(key) = __keys(array)
#define __test_keys(key, array) !__endp(__g(key))
#define __prep_keys(key, array) key = __car(__g(key))
#define __fini_keys(key, array) 1
#define __step_keys(key, array) __g(key) = __cdr(__g(key))
#define __temp___keys(key, array) __g(key),
#define __init___keys(key, array) __g(key) = __keys(array)
#define __test___keys(key, array) !__endp(__g(key))
#define __prep___keys(key, array) key = __car(__g(key))
#define __fini___keys(key, array) 1
#define __step___keys(key, array) __g(key) = __cdr(__g(key))
#define __temp_collect(var, expr)
#define __init_collect(var, expr) var = __list_begin()
#define __test_collect(var, expr) 1
#define __prep_collect(var, expr) var = __list_add(var, expr)
#define __fini_collect(var, expr) var = __list_end(var)
#define __step_collect(var, expr) 1
#define __temp_collect_plus(var, expr)
#define __init_collect_plus(var, expr) var = __list_begin()
#define __test_collect_plus(var, expr) 1
#define __prep_collect_plus(var, expr) var = __list_add(var, expr)
#define __fini_collect_plus(var, expr) var = __list_end(__list_add(var, expr))
#define __step_collect_plus(var, expr) 1
#define __temp_summing(var, expr)
#define __init_summing(var, expr) var = 0
#define __test_summing(var, expr) 1
#define __prep_summing(var, expr) var += (expr)
#define __fini_summing(var, expr) 1
#define __step_summing(var, expr) 1
function __loop_max(a, b)
{
return a > b ? a : b
}
#define __temp_maximizing(var, expr)
#define __init_maximizing(var, expr) var = nil
#define __test_maximizing(var, expr) 1
#define __prep_maximizing(var, expr) var = (__null(var) \
? expr \
: __loop_max(var, expr))
#define __fini_maximizing(var, expr) 1
#define __step_maximizing(var, expr) 1
function __loop_min(a, b)
{
return a > b ? b : a
}
#define __temp_minimizing(var, expr)
#define __init_minimizing(var, expr) var = nil
#define __test_minimizing(var, expr) 1
#define __prep_minimizing(var, expr) var = (__null(var) \
? expr \
: __loop_min(var, expr))
#define __fini_minimizing(var, expr) 1
#define __step_minimizing(var, expr) 1
function __loop_argmax(a, arga, b, argb)
{
return a > b ? arga : argb;
}
#define __ami(v) __gx(v, _max)
#define __amx(v) __gx(v, _min)
#define __amo(v) __gx(v, _old)
#define __temp_argmax(am, arg, expr) __amx(am), __amo(am),
#define __init_argmax(am, arg, expr) (__amx(am) = __nil) || (am = __nil)
#define __test_argmax(am, arg, expr) 1
#define __prep_argmax(am, arg, expr) ((__amo(am) = __amx(am)) || 1) && \
((__amx(am) = \
(__null(__amx(am)) \
? expr \
: __loop_max(__amx(am), \
expr))) || 1) && \
((__amo(am) != __amx(am)) ? am = arg : 1)
#define __fini_argmax(am, arg, expr) 1
#define __step_argmax(am, arg, expr) 1
function __loop_argmin(a, arga, b, argb)
{
return a < b ? arga : argb;
}
#define __temp_argmin(am, arg, expr) __ami(am), __amo(am),
#define __init_argmin(am, arg, expr) (__ami(am) = __nil) || (am = __nil)
#define __test_argmin(am, arg, expr) 1
#define __prep_argmin(am, arg, expr) ((__amo(am) = __ami(am)) || 1) && \
((__ami(am) = \
(__null(__ami(am)) \
? expr \
: __loop_min(__ami(am), \
expr))) || 1) && \
((__amo(am) != __ami(am)) ? am = arg : 1)
#define __fini_argmin(am, arg, expr) 1
#define __step_argmin(am, arg, expr) 1
#define __temp_counting(var, expr)
#define __init_counting(var, expr) var = 0
#define __test_counting(var, expr) 1
#define __prep_counting(var, expr) (expr) ? var++ : 1
#define __fini_counting(var, expr) 1
#define __step_counting(var, expr) 1
#define __temp_while(expr)
#define __init_while(expr) 1
#define __test_while(expr) expr
#define __prep_while(expr) 1
#define __fini_while(expr) 1
#define __step_while(expr) 1
#define __temp_until(expr)
#define __init_until(expr) 1
#define __test_until(expr) !(expr)
#define __prep_until(expr) 1
#define __fini_until(expr) 1
#define __step_until(expr) 1
#define __temp_parallel(...)
#define __init_parallel(...) __prog(__varexpand3(__init_first, __init_next, \
__VA_ARGS__))
#define __test_parallel(...) __nd(__varexpand3(__test_first, __test_next, \
__VA_ARGS__))
#define __prep_parallel(...) (__nd(__varexpand3(__prep_first, __prep_next, \
__VA_ARGS__)) || 1)
#define __fini_parallel(...) (__nd(__varexpand3(__fini_first, __fini_next, \
__VA_ARGS__)) && 0)
#define __step_parallel(...) __prog(__varexpand3(__step_first, __step_next, \
__VA_ARGS__))
#define __temp_if(test, clause)
#define __init_if(test, clause) __init_ ## clause
#define __test_if(test, clause) !(test) || __test_ ## clause
#define __prep_if(test, clause) (test) && __prep_ ## clause
#define __fini_if(test, clause) __fini_ ## clause
#define __step_if(test, clause) (test) && __step_ ## clause
#define __temp_records(file) __g(stream)
#define __init_records(file) __g(stream) = file
#define __test_records(file) (getline < __g(stream)) > 0
#define __prep_records(file) 1
#define __fini_records(file) __g(stream) != "-" ? close(__g(stream)) : 1
#define __step_records(file) 1
#endif
|