IncludeCPP 3.7.3__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of IncludeCPP might be problematic. Click here for more details.
- includecpp/__init__.py +59 -0
- includecpp/__init__.pyi +255 -0
- includecpp/__main__.py +4 -0
- includecpp/cli/__init__.py +4 -0
- includecpp/cli/commands.py +8270 -0
- includecpp/cli/config_parser.py +127 -0
- includecpp/core/__init__.py +19 -0
- includecpp/core/ai_integration.py +2132 -0
- includecpp/core/build_manager.py +2416 -0
- includecpp/core/cpp_api.py +376 -0
- includecpp/core/cpp_api.pyi +95 -0
- includecpp/core/cppy_converter.py +3448 -0
- includecpp/core/cssl/CSSL_DOCUMENTATION.md +2075 -0
- includecpp/core/cssl/__init__.py +42 -0
- includecpp/core/cssl/cssl_builtins.py +2271 -0
- includecpp/core/cssl/cssl_builtins.pyi +1393 -0
- includecpp/core/cssl/cssl_events.py +621 -0
- includecpp/core/cssl/cssl_modules.py +2803 -0
- includecpp/core/cssl/cssl_parser.py +2575 -0
- includecpp/core/cssl/cssl_runtime.py +3051 -0
- includecpp/core/cssl/cssl_syntax.py +488 -0
- includecpp/core/cssl/cssl_types.py +1512 -0
- includecpp/core/cssl_bridge.py +882 -0
- includecpp/core/cssl_bridge.pyi +488 -0
- includecpp/core/error_catalog.py +802 -0
- includecpp/core/error_formatter.py +1016 -0
- includecpp/core/exceptions.py +97 -0
- includecpp/core/path_discovery.py +77 -0
- includecpp/core/project_ui.py +3370 -0
- includecpp/core/settings_ui.py +326 -0
- includecpp/generator/__init__.py +1 -0
- includecpp/generator/parser.cpp +1903 -0
- includecpp/generator/parser.h +281 -0
- includecpp/generator/type_resolver.cpp +363 -0
- includecpp/generator/type_resolver.h +68 -0
- includecpp/py.typed +0 -0
- includecpp/templates/cpp.proj.template +18 -0
- includecpp/vscode/__init__.py +1 -0
- includecpp/vscode/cssl/__init__.py +1 -0
- includecpp/vscode/cssl/language-configuration.json +38 -0
- includecpp/vscode/cssl/package.json +50 -0
- includecpp/vscode/cssl/snippets/cssl.snippets.json +1080 -0
- includecpp/vscode/cssl/syntaxes/cssl.tmLanguage.json +341 -0
- includecpp-3.7.3.dist-info/METADATA +1076 -0
- includecpp-3.7.3.dist-info/RECORD +49 -0
- includecpp-3.7.3.dist-info/WHEEL +5 -0
- includecpp-3.7.3.dist-info/entry_points.txt +2 -0
- includecpp-3.7.3.dist-info/licenses/LICENSE +21 -0
- includecpp-3.7.3.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,1512 @@
|
|
|
1
|
+
"""
|
|
2
|
+
CSSL Data Types - Advanced container types for CSO Service Script Language
|
|
3
|
+
|
|
4
|
+
Types:
|
|
5
|
+
- datastruct<T>: Universal container (lazy declarator) - can hold any type
|
|
6
|
+
- shuffled<T>: Unorganized fast storage for multiple returns
|
|
7
|
+
- iterator<T>: Advanced iterator with programmable tasks
|
|
8
|
+
- combo<T>: Filter/search spaces for open parameter matching
|
|
9
|
+
- dataspace<T>: SQL/data storage container
|
|
10
|
+
- openquote<T>: SQL openquote container
|
|
11
|
+
"""
|
|
12
|
+
|
|
13
|
+
from typing import Any, Dict, List, Optional, Callable, Union, TypeVar, Generic
|
|
14
|
+
from dataclasses import dataclass, field
|
|
15
|
+
import copy
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
T = TypeVar('T')
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
class DataStruct(list):
|
|
22
|
+
"""Universal container - lazy declarator that can hold any type.
|
|
23
|
+
|
|
24
|
+
Like a vector but more flexible. Can hold strings, ints, floats,
|
|
25
|
+
objects, etc. at the cost of performance.
|
|
26
|
+
|
|
27
|
+
Usage:
|
|
28
|
+
datastruct<dynamic> myData;
|
|
29
|
+
myData +<== someValue;
|
|
30
|
+
myData.content() # Returns all elements
|
|
31
|
+
"""
|
|
32
|
+
|
|
33
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
34
|
+
super().__init__()
|
|
35
|
+
self._element_type = element_type
|
|
36
|
+
self._metadata: Dict[str, Any] = {}
|
|
37
|
+
|
|
38
|
+
def content(self) -> list:
|
|
39
|
+
"""Return all elements as a list"""
|
|
40
|
+
return list(self)
|
|
41
|
+
|
|
42
|
+
def add(self, item: Any) -> 'DataStruct':
|
|
43
|
+
"""Add an item to the datastruct"""
|
|
44
|
+
self.append(item)
|
|
45
|
+
return self
|
|
46
|
+
|
|
47
|
+
def remove_where(self, predicate: Callable[[Any], bool]) -> 'DataStruct':
|
|
48
|
+
"""Remove items matching predicate"""
|
|
49
|
+
to_remove = [item for item in self if predicate(item)]
|
|
50
|
+
for item in to_remove:
|
|
51
|
+
self.remove(item)
|
|
52
|
+
return self
|
|
53
|
+
|
|
54
|
+
def find_where(self, predicate: Callable[[Any], bool]) -> Optional[Any]:
|
|
55
|
+
"""Find first item matching predicate"""
|
|
56
|
+
for item in self:
|
|
57
|
+
if predicate(item):
|
|
58
|
+
return item
|
|
59
|
+
return None
|
|
60
|
+
|
|
61
|
+
def convert(self, target_type: type) -> Any:
|
|
62
|
+
"""Convert first element to target type"""
|
|
63
|
+
if len(self) > 0:
|
|
64
|
+
return target_type(self[0])
|
|
65
|
+
return None
|
|
66
|
+
|
|
67
|
+
def begin(self) -> int:
|
|
68
|
+
"""Return iterator to beginning (C++ style)"""
|
|
69
|
+
return 0
|
|
70
|
+
|
|
71
|
+
def end(self) -> int:
|
|
72
|
+
"""Return iterator to end (C++ style)"""
|
|
73
|
+
return len(self)
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
class Stack(list):
|
|
77
|
+
"""Stack data structure (LIFO).
|
|
78
|
+
|
|
79
|
+
Standard stack with push/pop operations.
|
|
80
|
+
|
|
81
|
+
Usage:
|
|
82
|
+
stack<string> myStack;
|
|
83
|
+
myStack.push("Item1");
|
|
84
|
+
myStack.push("Item2");
|
|
85
|
+
item = myStack.pop(); # Returns "Item2"
|
|
86
|
+
"""
|
|
87
|
+
|
|
88
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
89
|
+
super().__init__()
|
|
90
|
+
self._element_type = element_type
|
|
91
|
+
|
|
92
|
+
def push(self, item: Any) -> 'Stack':
|
|
93
|
+
"""Push item onto stack"""
|
|
94
|
+
self.append(item)
|
|
95
|
+
return self
|
|
96
|
+
|
|
97
|
+
def push_back(self, item: Any) -> 'Stack':
|
|
98
|
+
"""Push item onto stack (alias for push)"""
|
|
99
|
+
self.append(item)
|
|
100
|
+
return self
|
|
101
|
+
|
|
102
|
+
def peek(self) -> Any:
|
|
103
|
+
"""View top item without removing"""
|
|
104
|
+
return self[-1] if self else None
|
|
105
|
+
|
|
106
|
+
def is_empty(self) -> bool:
|
|
107
|
+
"""Check if stack is empty"""
|
|
108
|
+
return len(self) == 0
|
|
109
|
+
|
|
110
|
+
def isEmpty(self) -> bool:
|
|
111
|
+
"""Check if stack is empty (camelCase alias)"""
|
|
112
|
+
return len(self) == 0
|
|
113
|
+
|
|
114
|
+
def size(self) -> int:
|
|
115
|
+
"""Return stack size"""
|
|
116
|
+
return len(self)
|
|
117
|
+
|
|
118
|
+
def length(self) -> int:
|
|
119
|
+
"""Return stack length (alias for size)"""
|
|
120
|
+
return len(self)
|
|
121
|
+
|
|
122
|
+
def contains(self, item: Any) -> bool:
|
|
123
|
+
"""Check if stack contains item"""
|
|
124
|
+
return item in self
|
|
125
|
+
|
|
126
|
+
def indexOf(self, item: Any) -> int:
|
|
127
|
+
"""Find index of item (-1 if not found)"""
|
|
128
|
+
try:
|
|
129
|
+
return self.index(item)
|
|
130
|
+
except ValueError:
|
|
131
|
+
return -1
|
|
132
|
+
|
|
133
|
+
def toArray(self) -> list:
|
|
134
|
+
"""Convert stack to array"""
|
|
135
|
+
return list(self)
|
|
136
|
+
|
|
137
|
+
def swap(self) -> 'Stack':
|
|
138
|
+
"""Swap top two elements"""
|
|
139
|
+
if len(self) >= 2:
|
|
140
|
+
self[-1], self[-2] = self[-2], self[-1]
|
|
141
|
+
return self
|
|
142
|
+
|
|
143
|
+
def dup(self) -> 'Stack':
|
|
144
|
+
"""Duplicate top element"""
|
|
145
|
+
if self:
|
|
146
|
+
self.append(self[-1])
|
|
147
|
+
return self
|
|
148
|
+
|
|
149
|
+
def begin(self) -> int:
|
|
150
|
+
"""Return iterator to beginning (C++ style)"""
|
|
151
|
+
return 0
|
|
152
|
+
|
|
153
|
+
def end(self) -> int:
|
|
154
|
+
"""Return iterator to end (C++ style)"""
|
|
155
|
+
return len(self)
|
|
156
|
+
|
|
157
|
+
|
|
158
|
+
class Vector(list):
|
|
159
|
+
"""Dynamic array (vector) data structure.
|
|
160
|
+
|
|
161
|
+
Resizable array with efficient random access.
|
|
162
|
+
|
|
163
|
+
Usage:
|
|
164
|
+
vector<int> myVector;
|
|
165
|
+
myVector.push(1);
|
|
166
|
+
myVector.push(2);
|
|
167
|
+
myVector.at(0); # Returns 1
|
|
168
|
+
"""
|
|
169
|
+
|
|
170
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
171
|
+
super().__init__()
|
|
172
|
+
self._element_type = element_type
|
|
173
|
+
|
|
174
|
+
def push(self, item: Any) -> 'Vector':
|
|
175
|
+
"""Add item to end"""
|
|
176
|
+
self.append(item)
|
|
177
|
+
return self
|
|
178
|
+
|
|
179
|
+
def push_back(self, item: Any) -> 'Vector':
|
|
180
|
+
"""Add item to end (alias for push)"""
|
|
181
|
+
self.append(item)
|
|
182
|
+
return self
|
|
183
|
+
|
|
184
|
+
def push_front(self, item: Any) -> 'Vector':
|
|
185
|
+
"""Add item to front"""
|
|
186
|
+
self.insert(0, item)
|
|
187
|
+
return self
|
|
188
|
+
|
|
189
|
+
def pop_back(self) -> Any:
|
|
190
|
+
"""Remove and return last element"""
|
|
191
|
+
return self.pop() if self else None
|
|
192
|
+
|
|
193
|
+
def pop_front(self) -> Any:
|
|
194
|
+
"""Remove and return first element"""
|
|
195
|
+
return self.pop(0) if self else None
|
|
196
|
+
|
|
197
|
+
def at(self, index: int) -> Any:
|
|
198
|
+
"""Get item at index"""
|
|
199
|
+
if 0 <= index < len(self):
|
|
200
|
+
return self[index]
|
|
201
|
+
return None
|
|
202
|
+
|
|
203
|
+
def set(self, index: int, value: Any) -> 'Vector':
|
|
204
|
+
"""Set item at index"""
|
|
205
|
+
if 0 <= index < len(self):
|
|
206
|
+
self[index] = value
|
|
207
|
+
return self
|
|
208
|
+
|
|
209
|
+
def size(self) -> int:
|
|
210
|
+
"""Return vector size"""
|
|
211
|
+
return len(self)
|
|
212
|
+
|
|
213
|
+
def length(self) -> int:
|
|
214
|
+
"""Return vector length (alias for size)"""
|
|
215
|
+
return len(self)
|
|
216
|
+
|
|
217
|
+
def empty(self) -> bool:
|
|
218
|
+
"""Check if vector is empty"""
|
|
219
|
+
return len(self) == 0
|
|
220
|
+
|
|
221
|
+
def isEmpty(self) -> bool:
|
|
222
|
+
"""Check if vector is empty (camelCase alias)"""
|
|
223
|
+
return len(self) == 0
|
|
224
|
+
|
|
225
|
+
def front(self) -> Any:
|
|
226
|
+
"""Get first element"""
|
|
227
|
+
return self[0] if self else None
|
|
228
|
+
|
|
229
|
+
def back(self) -> Any:
|
|
230
|
+
"""Get last element"""
|
|
231
|
+
return self[-1] if self else None
|
|
232
|
+
|
|
233
|
+
def contains(self, item: Any) -> bool:
|
|
234
|
+
"""Check if vector contains item"""
|
|
235
|
+
return item in self
|
|
236
|
+
|
|
237
|
+
def indexOf(self, item: Any) -> int:
|
|
238
|
+
"""Find index of item (-1 if not found)"""
|
|
239
|
+
try:
|
|
240
|
+
return self.index(item)
|
|
241
|
+
except ValueError:
|
|
242
|
+
return -1
|
|
243
|
+
|
|
244
|
+
def lastIndexOf(self, item: Any) -> int:
|
|
245
|
+
"""Find last index of item (-1 if not found)"""
|
|
246
|
+
for i in range(len(self) - 1, -1, -1):
|
|
247
|
+
if self[i] == item:
|
|
248
|
+
return i
|
|
249
|
+
return -1
|
|
250
|
+
|
|
251
|
+
def find(self, predicate: Callable[[Any], bool]) -> Any:
|
|
252
|
+
"""Find first item matching predicate"""
|
|
253
|
+
for item in self:
|
|
254
|
+
if callable(predicate) and predicate(item):
|
|
255
|
+
return item
|
|
256
|
+
elif item == predicate:
|
|
257
|
+
return item
|
|
258
|
+
return None
|
|
259
|
+
|
|
260
|
+
def findIndex(self, predicate: Callable[[Any], bool]) -> int:
|
|
261
|
+
"""Find index of first item matching predicate"""
|
|
262
|
+
for i, item in enumerate(self):
|
|
263
|
+
if callable(predicate) and predicate(item):
|
|
264
|
+
return i
|
|
265
|
+
elif item == predicate:
|
|
266
|
+
return i
|
|
267
|
+
return -1
|
|
268
|
+
|
|
269
|
+
def slice(self, start: int, end: int = None) -> 'Vector':
|
|
270
|
+
"""Return slice of vector"""
|
|
271
|
+
if end is None:
|
|
272
|
+
result = Vector(self._element_type)
|
|
273
|
+
result.extend(self[start:])
|
|
274
|
+
else:
|
|
275
|
+
result = Vector(self._element_type)
|
|
276
|
+
result.extend(self[start:end])
|
|
277
|
+
return result
|
|
278
|
+
|
|
279
|
+
def join(self, separator: str = ',') -> str:
|
|
280
|
+
"""Join elements into string"""
|
|
281
|
+
return separator.join(str(item) for item in self)
|
|
282
|
+
|
|
283
|
+
def map(self, func: Callable[[Any], Any]) -> 'Vector':
|
|
284
|
+
"""Apply function to all elements"""
|
|
285
|
+
result = Vector(self._element_type)
|
|
286
|
+
result.extend(func(item) for item in self)
|
|
287
|
+
return result
|
|
288
|
+
|
|
289
|
+
def filter(self, predicate: Callable[[Any], bool]) -> 'Vector':
|
|
290
|
+
"""Filter elements by predicate"""
|
|
291
|
+
result = Vector(self._element_type)
|
|
292
|
+
result.extend(item for item in self if predicate(item))
|
|
293
|
+
return result
|
|
294
|
+
|
|
295
|
+
def forEach(self, func: Callable[[Any], None]) -> 'Vector':
|
|
296
|
+
"""Execute function for each element"""
|
|
297
|
+
for item in self:
|
|
298
|
+
func(item)
|
|
299
|
+
return self
|
|
300
|
+
|
|
301
|
+
def toArray(self) -> list:
|
|
302
|
+
"""Convert to plain list"""
|
|
303
|
+
return list(self)
|
|
304
|
+
|
|
305
|
+
def fill(self, value: Any, start: int = 0, end: int = None) -> 'Vector':
|
|
306
|
+
"""Fill range with value"""
|
|
307
|
+
if end is None:
|
|
308
|
+
end = len(self)
|
|
309
|
+
for i in range(start, min(end, len(self))):
|
|
310
|
+
self[i] = value
|
|
311
|
+
return self
|
|
312
|
+
|
|
313
|
+
def every(self, predicate: Callable[[Any], bool]) -> bool:
|
|
314
|
+
"""Check if all elements match predicate"""
|
|
315
|
+
return all(predicate(item) for item in self)
|
|
316
|
+
|
|
317
|
+
def some(self, predicate: Callable[[Any], bool]) -> bool:
|
|
318
|
+
"""Check if any element matches predicate"""
|
|
319
|
+
return any(predicate(item) for item in self)
|
|
320
|
+
|
|
321
|
+
def reduce(self, func: Callable[[Any, Any], Any], initial: Any = None) -> Any:
|
|
322
|
+
"""Reduce vector to single value"""
|
|
323
|
+
from functools import reduce as py_reduce
|
|
324
|
+
if initial is None:
|
|
325
|
+
return py_reduce(func, self)
|
|
326
|
+
return py_reduce(func, self, initial)
|
|
327
|
+
|
|
328
|
+
def begin(self) -> int:
|
|
329
|
+
"""Return iterator to beginning (C++ style)"""
|
|
330
|
+
return 0
|
|
331
|
+
|
|
332
|
+
def end(self) -> int:
|
|
333
|
+
"""Return iterator to end (C++ style)"""
|
|
334
|
+
return len(self)
|
|
335
|
+
|
|
336
|
+
|
|
337
|
+
class Array(list):
|
|
338
|
+
"""Array data structure with CSSL methods.
|
|
339
|
+
|
|
340
|
+
Standard array with push/pop/length operations.
|
|
341
|
+
|
|
342
|
+
Usage:
|
|
343
|
+
array<string> arr;
|
|
344
|
+
arr.push("Item");
|
|
345
|
+
arr.length(); # Returns 1
|
|
346
|
+
"""
|
|
347
|
+
|
|
348
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
349
|
+
super().__init__()
|
|
350
|
+
self._element_type = element_type
|
|
351
|
+
|
|
352
|
+
def push(self, item: Any) -> 'Array':
|
|
353
|
+
"""Add item to end"""
|
|
354
|
+
self.append(item)
|
|
355
|
+
return self
|
|
356
|
+
|
|
357
|
+
def push_back(self, item: Any) -> 'Array':
|
|
358
|
+
"""Add item to end (alias for push)"""
|
|
359
|
+
self.append(item)
|
|
360
|
+
return self
|
|
361
|
+
|
|
362
|
+
def push_front(self, item: Any) -> 'Array':
|
|
363
|
+
"""Add item to front"""
|
|
364
|
+
self.insert(0, item)
|
|
365
|
+
return self
|
|
366
|
+
|
|
367
|
+
def pop_back(self) -> Any:
|
|
368
|
+
"""Remove and return last element"""
|
|
369
|
+
return self.pop() if self else None
|
|
370
|
+
|
|
371
|
+
def pop_front(self) -> Any:
|
|
372
|
+
"""Remove and return first element"""
|
|
373
|
+
return self.pop(0) if self else None
|
|
374
|
+
|
|
375
|
+
def at(self, index: int) -> Any:
|
|
376
|
+
"""Get item at index"""
|
|
377
|
+
if 0 <= index < len(self):
|
|
378
|
+
return self[index]
|
|
379
|
+
return None
|
|
380
|
+
|
|
381
|
+
def set(self, index: int, value: Any) -> 'Array':
|
|
382
|
+
"""Set item at index"""
|
|
383
|
+
if 0 <= index < len(self):
|
|
384
|
+
self[index] = value
|
|
385
|
+
return self
|
|
386
|
+
|
|
387
|
+
def size(self) -> int:
|
|
388
|
+
"""Return array size"""
|
|
389
|
+
return len(self)
|
|
390
|
+
|
|
391
|
+
def length(self) -> int:
|
|
392
|
+
"""Return array length"""
|
|
393
|
+
return len(self)
|
|
394
|
+
|
|
395
|
+
def empty(self) -> bool:
|
|
396
|
+
"""Check if array is empty"""
|
|
397
|
+
return len(self) == 0
|
|
398
|
+
|
|
399
|
+
def isEmpty(self) -> bool:
|
|
400
|
+
"""Check if array is empty (camelCase alias)"""
|
|
401
|
+
return len(self) == 0
|
|
402
|
+
|
|
403
|
+
def first(self) -> Any:
|
|
404
|
+
"""Get first element"""
|
|
405
|
+
return self[0] if self else None
|
|
406
|
+
|
|
407
|
+
def last(self) -> Any:
|
|
408
|
+
"""Get last element"""
|
|
409
|
+
return self[-1] if self else None
|
|
410
|
+
|
|
411
|
+
def contains(self, item: Any) -> bool:
|
|
412
|
+
"""Check if array contains item"""
|
|
413
|
+
return item in self
|
|
414
|
+
|
|
415
|
+
def indexOf(self, item: Any) -> int:
|
|
416
|
+
"""Find index of item (-1 if not found)"""
|
|
417
|
+
try:
|
|
418
|
+
return self.index(item)
|
|
419
|
+
except ValueError:
|
|
420
|
+
return -1
|
|
421
|
+
|
|
422
|
+
def lastIndexOf(self, item: Any) -> int:
|
|
423
|
+
"""Find last index of item (-1 if not found)"""
|
|
424
|
+
for i in range(len(self) - 1, -1, -1):
|
|
425
|
+
if self[i] == item:
|
|
426
|
+
return i
|
|
427
|
+
return -1
|
|
428
|
+
|
|
429
|
+
def find(self, predicate: Callable[[Any], bool]) -> Any:
|
|
430
|
+
"""Find first item matching predicate"""
|
|
431
|
+
for item in self:
|
|
432
|
+
if callable(predicate) and predicate(item):
|
|
433
|
+
return item
|
|
434
|
+
elif item == predicate:
|
|
435
|
+
return item
|
|
436
|
+
return None
|
|
437
|
+
|
|
438
|
+
def findIndex(self, predicate: Callable[[Any], bool]) -> int:
|
|
439
|
+
"""Find index of first item matching predicate"""
|
|
440
|
+
for i, item in enumerate(self):
|
|
441
|
+
if callable(predicate) and predicate(item):
|
|
442
|
+
return i
|
|
443
|
+
elif item == predicate:
|
|
444
|
+
return i
|
|
445
|
+
return -1
|
|
446
|
+
|
|
447
|
+
def slice(self, start: int, end: int = None) -> 'Array':
|
|
448
|
+
"""Return slice of array"""
|
|
449
|
+
if end is None:
|
|
450
|
+
result = Array(self._element_type)
|
|
451
|
+
result.extend(self[start:])
|
|
452
|
+
else:
|
|
453
|
+
result = Array(self._element_type)
|
|
454
|
+
result.extend(self[start:end])
|
|
455
|
+
return result
|
|
456
|
+
|
|
457
|
+
def join(self, separator: str = ',') -> str:
|
|
458
|
+
"""Join elements into string"""
|
|
459
|
+
return separator.join(str(item) for item in self)
|
|
460
|
+
|
|
461
|
+
def map(self, func: Callable[[Any], Any]) -> 'Array':
|
|
462
|
+
"""Apply function to all elements"""
|
|
463
|
+
result = Array(self._element_type)
|
|
464
|
+
result.extend(func(item) for item in self)
|
|
465
|
+
return result
|
|
466
|
+
|
|
467
|
+
def filter(self, predicate: Callable[[Any], bool]) -> 'Array':
|
|
468
|
+
"""Filter elements by predicate"""
|
|
469
|
+
result = Array(self._element_type)
|
|
470
|
+
result.extend(item for item in self if predicate(item))
|
|
471
|
+
return result
|
|
472
|
+
|
|
473
|
+
def forEach(self, func: Callable[[Any], None]) -> 'Array':
|
|
474
|
+
"""Execute function for each element"""
|
|
475
|
+
for item in self:
|
|
476
|
+
func(item)
|
|
477
|
+
return self
|
|
478
|
+
|
|
479
|
+
def toArray(self) -> list:
|
|
480
|
+
"""Convert to plain list"""
|
|
481
|
+
return list(self)
|
|
482
|
+
|
|
483
|
+
def fill(self, value: Any, start: int = 0, end: int = None) -> 'Array':
|
|
484
|
+
"""Fill range with value"""
|
|
485
|
+
if end is None:
|
|
486
|
+
end = len(self)
|
|
487
|
+
for i in range(start, min(end, len(self))):
|
|
488
|
+
self[i] = value
|
|
489
|
+
return self
|
|
490
|
+
|
|
491
|
+
def every(self, predicate: Callable[[Any], bool]) -> bool:
|
|
492
|
+
"""Check if all elements match predicate"""
|
|
493
|
+
return all(predicate(item) for item in self)
|
|
494
|
+
|
|
495
|
+
def some(self, predicate: Callable[[Any], bool]) -> bool:
|
|
496
|
+
"""Check if any element matches predicate"""
|
|
497
|
+
return any(predicate(item) for item in self)
|
|
498
|
+
|
|
499
|
+
def reduce(self, func: Callable[[Any, Any], Any], initial: Any = None) -> Any:
|
|
500
|
+
"""Reduce array to single value"""
|
|
501
|
+
from functools import reduce as py_reduce
|
|
502
|
+
if initial is None:
|
|
503
|
+
return py_reduce(func, self)
|
|
504
|
+
return py_reduce(func, self, initial)
|
|
505
|
+
|
|
506
|
+
def concat(self, *arrays) -> 'Array':
|
|
507
|
+
"""Concatenate with other arrays"""
|
|
508
|
+
result = Array(self._element_type)
|
|
509
|
+
result.extend(self)
|
|
510
|
+
for arr in arrays:
|
|
511
|
+
result.extend(arr)
|
|
512
|
+
return result
|
|
513
|
+
|
|
514
|
+
def flat(self, depth: int = 1) -> 'Array':
|
|
515
|
+
"""Flatten nested arrays"""
|
|
516
|
+
result = Array(self._element_type)
|
|
517
|
+
for item in self:
|
|
518
|
+
if isinstance(item, (list, Array)) and depth > 0:
|
|
519
|
+
if depth == 1:
|
|
520
|
+
result.extend(item)
|
|
521
|
+
else:
|
|
522
|
+
nested = Array(self._element_type)
|
|
523
|
+
nested.extend(item)
|
|
524
|
+
result.extend(nested.flat(depth - 1))
|
|
525
|
+
else:
|
|
526
|
+
result.append(item)
|
|
527
|
+
return result
|
|
528
|
+
|
|
529
|
+
def unique(self) -> 'Array':
|
|
530
|
+
"""Return array with unique elements"""
|
|
531
|
+
result = Array(self._element_type)
|
|
532
|
+
seen = set()
|
|
533
|
+
for item in self:
|
|
534
|
+
key = item if isinstance(item, (int, str, float, bool)) else id(item)
|
|
535
|
+
if key not in seen:
|
|
536
|
+
seen.add(key)
|
|
537
|
+
result.append(item)
|
|
538
|
+
return result
|
|
539
|
+
|
|
540
|
+
def begin(self) -> int:
|
|
541
|
+
"""Return iterator to beginning (C++ style)"""
|
|
542
|
+
return 0
|
|
543
|
+
|
|
544
|
+
def end(self) -> int:
|
|
545
|
+
"""Return iterator to end (C++ style)"""
|
|
546
|
+
return len(self)
|
|
547
|
+
|
|
548
|
+
|
|
549
|
+
class List(list):
|
|
550
|
+
"""Python-like list with all standard operations.
|
|
551
|
+
|
|
552
|
+
Works exactly like Python lists with additional CSSL methods.
|
|
553
|
+
|
|
554
|
+
Usage:
|
|
555
|
+
list myList;
|
|
556
|
+
myList.append("item");
|
|
557
|
+
myList.insert(0, "first");
|
|
558
|
+
myList.pop();
|
|
559
|
+
myList.find("item"); # Returns index or -1
|
|
560
|
+
"""
|
|
561
|
+
|
|
562
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
563
|
+
super().__init__()
|
|
564
|
+
self._element_type = element_type
|
|
565
|
+
|
|
566
|
+
def length(self) -> int:
|
|
567
|
+
"""Return list length"""
|
|
568
|
+
return len(self)
|
|
569
|
+
|
|
570
|
+
def size(self) -> int:
|
|
571
|
+
"""Return list size (alias for length)"""
|
|
572
|
+
return len(self)
|
|
573
|
+
|
|
574
|
+
def isEmpty(self) -> bool:
|
|
575
|
+
"""Check if list is empty"""
|
|
576
|
+
return len(self) == 0
|
|
577
|
+
|
|
578
|
+
def first(self) -> Any:
|
|
579
|
+
"""Get first element"""
|
|
580
|
+
return self[0] if self else None
|
|
581
|
+
|
|
582
|
+
def last(self) -> Any:
|
|
583
|
+
"""Get last element"""
|
|
584
|
+
return self[-1] if self else None
|
|
585
|
+
|
|
586
|
+
def at(self, index: int) -> Any:
|
|
587
|
+
"""Get item at index (safe access)"""
|
|
588
|
+
if 0 <= index < len(self):
|
|
589
|
+
return self[index]
|
|
590
|
+
return None
|
|
591
|
+
|
|
592
|
+
def set(self, index: int, value: Any) -> 'List':
|
|
593
|
+
"""Set item at index"""
|
|
594
|
+
if 0 <= index < len(self):
|
|
595
|
+
self[index] = value
|
|
596
|
+
return self
|
|
597
|
+
|
|
598
|
+
def add(self, item: Any) -> 'List':
|
|
599
|
+
"""Add item to end (alias for append)"""
|
|
600
|
+
self.append(item)
|
|
601
|
+
return self
|
|
602
|
+
|
|
603
|
+
def push(self, item: Any) -> 'List':
|
|
604
|
+
"""Push item to end (alias for append)"""
|
|
605
|
+
self.append(item)
|
|
606
|
+
return self
|
|
607
|
+
|
|
608
|
+
def find(self, item: Any) -> int:
|
|
609
|
+
"""Find index of item (-1 if not found)"""
|
|
610
|
+
try:
|
|
611
|
+
return self.index(item)
|
|
612
|
+
except ValueError:
|
|
613
|
+
return -1
|
|
614
|
+
|
|
615
|
+
def contains(self, item: Any) -> bool:
|
|
616
|
+
"""Check if list contains item"""
|
|
617
|
+
return item in self
|
|
618
|
+
|
|
619
|
+
def indexOf(self, item: Any) -> int:
|
|
620
|
+
"""Find index of item (-1 if not found)"""
|
|
621
|
+
return self.find(item)
|
|
622
|
+
|
|
623
|
+
def lastIndexOf(self, item: Any) -> int:
|
|
624
|
+
"""Find last index of item (-1 if not found)"""
|
|
625
|
+
for i in range(len(self) - 1, -1, -1):
|
|
626
|
+
if self[i] == item:
|
|
627
|
+
return i
|
|
628
|
+
return -1
|
|
629
|
+
|
|
630
|
+
def removeAt(self, index: int) -> Any:
|
|
631
|
+
"""Remove and return item at index"""
|
|
632
|
+
if 0 <= index < len(self):
|
|
633
|
+
return self.pop(index)
|
|
634
|
+
return None
|
|
635
|
+
|
|
636
|
+
def removeValue(self, value: Any) -> bool:
|
|
637
|
+
"""Remove first occurrence of value"""
|
|
638
|
+
try:
|
|
639
|
+
self.remove(value)
|
|
640
|
+
return True
|
|
641
|
+
except ValueError:
|
|
642
|
+
return False
|
|
643
|
+
|
|
644
|
+
def removeAll(self, value: Any) -> int:
|
|
645
|
+
"""Remove all occurrences of value, return count"""
|
|
646
|
+
count = 0
|
|
647
|
+
while value in self:
|
|
648
|
+
self.remove(value)
|
|
649
|
+
count += 1
|
|
650
|
+
return count
|
|
651
|
+
|
|
652
|
+
def slice(self, start: int, end: int = None) -> 'List':
|
|
653
|
+
"""Return slice of list"""
|
|
654
|
+
result = List(self._element_type)
|
|
655
|
+
if end is None:
|
|
656
|
+
result.extend(self[start:])
|
|
657
|
+
else:
|
|
658
|
+
result.extend(self[start:end])
|
|
659
|
+
return result
|
|
660
|
+
|
|
661
|
+
def join(self, separator: str = ',') -> str:
|
|
662
|
+
"""Join elements into string"""
|
|
663
|
+
return separator.join(str(item) for item in self)
|
|
664
|
+
|
|
665
|
+
def unique(self) -> 'List':
|
|
666
|
+
"""Return list with unique elements"""
|
|
667
|
+
result = List(self._element_type)
|
|
668
|
+
seen = set()
|
|
669
|
+
for item in self:
|
|
670
|
+
key = item if isinstance(item, (int, str, float, bool)) else id(item)
|
|
671
|
+
if key not in seen:
|
|
672
|
+
seen.add(key)
|
|
673
|
+
result.append(item)
|
|
674
|
+
return result
|
|
675
|
+
|
|
676
|
+
def sorted(self, reverse: bool = False) -> 'List':
|
|
677
|
+
"""Return sorted copy"""
|
|
678
|
+
result = List(self._element_type)
|
|
679
|
+
result.extend(sorted(self, reverse=reverse))
|
|
680
|
+
return result
|
|
681
|
+
|
|
682
|
+
def reversed(self) -> 'List':
|
|
683
|
+
"""Return reversed copy"""
|
|
684
|
+
result = List(self._element_type)
|
|
685
|
+
result.extend(reversed(self))
|
|
686
|
+
return result
|
|
687
|
+
|
|
688
|
+
def shuffle(self) -> 'List':
|
|
689
|
+
"""Shuffle list in place"""
|
|
690
|
+
import random
|
|
691
|
+
random.shuffle(self)
|
|
692
|
+
return self
|
|
693
|
+
|
|
694
|
+
def fill(self, value: Any, count: int = None) -> 'List':
|
|
695
|
+
"""Fill list with value"""
|
|
696
|
+
if count is None:
|
|
697
|
+
for i in range(len(self)):
|
|
698
|
+
self[i] = value
|
|
699
|
+
else:
|
|
700
|
+
self.clear()
|
|
701
|
+
self.extend([value] * count)
|
|
702
|
+
return self
|
|
703
|
+
|
|
704
|
+
def begin(self) -> int:
|
|
705
|
+
"""Return iterator to beginning"""
|
|
706
|
+
return 0
|
|
707
|
+
|
|
708
|
+
def end(self) -> int:
|
|
709
|
+
"""Return iterator to end"""
|
|
710
|
+
return len(self)
|
|
711
|
+
|
|
712
|
+
|
|
713
|
+
class Dictionary(dict):
|
|
714
|
+
"""Python-like dictionary with all standard operations.
|
|
715
|
+
|
|
716
|
+
Works exactly like Python dicts with additional CSSL methods.
|
|
717
|
+
|
|
718
|
+
Usage:
|
|
719
|
+
dictionary myDict;
|
|
720
|
+
myDict.set("key", "value");
|
|
721
|
+
myDict.get("key");
|
|
722
|
+
myDict.keys();
|
|
723
|
+
myDict.values();
|
|
724
|
+
"""
|
|
725
|
+
|
|
726
|
+
def __init__(self, key_type: str = 'dynamic', value_type: str = 'dynamic'):
|
|
727
|
+
super().__init__()
|
|
728
|
+
self._key_type = key_type
|
|
729
|
+
self._value_type = value_type
|
|
730
|
+
|
|
731
|
+
def length(self) -> int:
|
|
732
|
+
"""Return dictionary size"""
|
|
733
|
+
return len(self)
|
|
734
|
+
|
|
735
|
+
def size(self) -> int:
|
|
736
|
+
"""Return dictionary size (alias for length)"""
|
|
737
|
+
return len(self)
|
|
738
|
+
|
|
739
|
+
def isEmpty(self) -> bool:
|
|
740
|
+
"""Check if dictionary is empty"""
|
|
741
|
+
return len(self) == 0
|
|
742
|
+
|
|
743
|
+
def set(self, key: Any, value: Any) -> 'Dictionary':
|
|
744
|
+
"""Set key-value pair"""
|
|
745
|
+
self[key] = value
|
|
746
|
+
return self
|
|
747
|
+
|
|
748
|
+
def hasKey(self, key: Any) -> bool:
|
|
749
|
+
"""Check if key exists"""
|
|
750
|
+
return key in self
|
|
751
|
+
|
|
752
|
+
def hasValue(self, value: Any) -> bool:
|
|
753
|
+
"""Check if value exists"""
|
|
754
|
+
return value in self.values()
|
|
755
|
+
|
|
756
|
+
def remove(self, key: Any) -> Any:
|
|
757
|
+
"""Remove and return value for key"""
|
|
758
|
+
return self.pop(key, None)
|
|
759
|
+
|
|
760
|
+
def getOrDefault(self, key: Any, default: Any = None) -> Any:
|
|
761
|
+
"""Get value or default if not found"""
|
|
762
|
+
return self.get(key, default)
|
|
763
|
+
|
|
764
|
+
def setDefault(self, key: Any, default: Any) -> Any:
|
|
765
|
+
"""Set default if key doesn't exist, return value"""
|
|
766
|
+
if key not in self:
|
|
767
|
+
self[key] = default
|
|
768
|
+
return self[key]
|
|
769
|
+
|
|
770
|
+
def merge(self, other: dict) -> 'Dictionary':
|
|
771
|
+
"""Merge another dictionary into this one"""
|
|
772
|
+
self.update(other)
|
|
773
|
+
return self
|
|
774
|
+
|
|
775
|
+
def keysList(self) -> list:
|
|
776
|
+
"""Return keys as list"""
|
|
777
|
+
return list(self.keys())
|
|
778
|
+
|
|
779
|
+
def valuesList(self) -> list:
|
|
780
|
+
"""Return values as list"""
|
|
781
|
+
return list(self.values())
|
|
782
|
+
|
|
783
|
+
def itemsList(self) -> list:
|
|
784
|
+
"""Return items as list of tuples"""
|
|
785
|
+
return list(self.items())
|
|
786
|
+
|
|
787
|
+
def filter(self, predicate: Callable[[Any, Any], bool]) -> 'Dictionary':
|
|
788
|
+
"""Filter dictionary by predicate(key, value)"""
|
|
789
|
+
result = Dictionary(self._key_type, self._value_type)
|
|
790
|
+
for k, v in self.items():
|
|
791
|
+
if predicate(k, v):
|
|
792
|
+
result[k] = v
|
|
793
|
+
return result
|
|
794
|
+
|
|
795
|
+
def map(self, func: Callable[[Any, Any], Any]) -> 'Dictionary':
|
|
796
|
+
"""Apply function to all values"""
|
|
797
|
+
result = Dictionary(self._key_type, self._value_type)
|
|
798
|
+
for k, v in self.items():
|
|
799
|
+
result[k] = func(k, v)
|
|
800
|
+
return result
|
|
801
|
+
|
|
802
|
+
def forEach(self, func: Callable[[Any, Any], None]) -> 'Dictionary':
|
|
803
|
+
"""Execute function for each key-value pair"""
|
|
804
|
+
for k, v in self.items():
|
|
805
|
+
func(k, v)
|
|
806
|
+
return self
|
|
807
|
+
|
|
808
|
+
def invert(self) -> 'Dictionary':
|
|
809
|
+
"""Swap keys and values"""
|
|
810
|
+
result = Dictionary(self._value_type, self._key_type)
|
|
811
|
+
for k, v in self.items():
|
|
812
|
+
result[v] = k
|
|
813
|
+
return result
|
|
814
|
+
|
|
815
|
+
def find(self, value: Any) -> Optional[Any]:
|
|
816
|
+
"""Find first key with given value"""
|
|
817
|
+
for k, v in self.items():
|
|
818
|
+
if v == value:
|
|
819
|
+
return k
|
|
820
|
+
return None
|
|
821
|
+
|
|
822
|
+
def findAll(self, value: Any) -> list:
|
|
823
|
+
"""Find all keys with given value"""
|
|
824
|
+
return [k for k, v in self.items() if v == value]
|
|
825
|
+
|
|
826
|
+
|
|
827
|
+
class Shuffled(list):
|
|
828
|
+
"""Unorganized fast storage for multiple returns.
|
|
829
|
+
|
|
830
|
+
Stores data unorganized for fast and efficient access.
|
|
831
|
+
Supports receiving multiple return values from functions.
|
|
832
|
+
Can be used as a function modifier to allow multiple returns.
|
|
833
|
+
|
|
834
|
+
Usage:
|
|
835
|
+
shuffled<string> results;
|
|
836
|
+
results +<== someFunc(); # Catches all returns
|
|
837
|
+
results.read() # Returns all content as list
|
|
838
|
+
|
|
839
|
+
# As return modifier:
|
|
840
|
+
shuffled string getData() {
|
|
841
|
+
return "name", "address"; # Returns multiple values
|
|
842
|
+
}
|
|
843
|
+
"""
|
|
844
|
+
|
|
845
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
846
|
+
super().__init__()
|
|
847
|
+
self._element_type = element_type
|
|
848
|
+
|
|
849
|
+
def read(self) -> list:
|
|
850
|
+
"""Return all content as a list"""
|
|
851
|
+
return list(self)
|
|
852
|
+
|
|
853
|
+
def collect(self, func: Callable, *args) -> 'Shuffled':
|
|
854
|
+
"""Collect all returns from a function"""
|
|
855
|
+
result = func(*args)
|
|
856
|
+
if isinstance(result, (list, tuple)):
|
|
857
|
+
self.extend(result)
|
|
858
|
+
else:
|
|
859
|
+
self.append(result)
|
|
860
|
+
return self
|
|
861
|
+
|
|
862
|
+
def add(self, *items) -> 'Shuffled':
|
|
863
|
+
"""Add one or more items"""
|
|
864
|
+
for item in items:
|
|
865
|
+
if isinstance(item, (list, tuple)):
|
|
866
|
+
self.extend(item)
|
|
867
|
+
else:
|
|
868
|
+
self.append(item)
|
|
869
|
+
return self
|
|
870
|
+
|
|
871
|
+
def first(self) -> Any:
|
|
872
|
+
"""Get first element"""
|
|
873
|
+
return self[0] if self else None
|
|
874
|
+
|
|
875
|
+
def last(self) -> Any:
|
|
876
|
+
"""Get last element"""
|
|
877
|
+
return self[-1] if self else None
|
|
878
|
+
|
|
879
|
+
def length(self) -> int:
|
|
880
|
+
"""Return shuffled length"""
|
|
881
|
+
return len(self)
|
|
882
|
+
|
|
883
|
+
def isEmpty(self) -> bool:
|
|
884
|
+
"""Check if empty"""
|
|
885
|
+
return len(self) == 0
|
|
886
|
+
|
|
887
|
+
def contains(self, item: Any) -> bool:
|
|
888
|
+
"""Check if contains item"""
|
|
889
|
+
return item in self
|
|
890
|
+
|
|
891
|
+
def at(self, index: int) -> Any:
|
|
892
|
+
"""Get item at index"""
|
|
893
|
+
if 0 <= index < len(self):
|
|
894
|
+
return self[index]
|
|
895
|
+
return None
|
|
896
|
+
|
|
897
|
+
def toList(self) -> list:
|
|
898
|
+
"""Convert to plain list"""
|
|
899
|
+
return list(self)
|
|
900
|
+
|
|
901
|
+
def toTuple(self) -> tuple:
|
|
902
|
+
"""Convert to tuple"""
|
|
903
|
+
return tuple(self)
|
|
904
|
+
|
|
905
|
+
|
|
906
|
+
class Iterator:
|
|
907
|
+
"""Advanced iterator with programmable tasks.
|
|
908
|
+
|
|
909
|
+
Provides iterator positions within a data container with
|
|
910
|
+
the ability to attach tasks (functions) to iterators.
|
|
911
|
+
|
|
912
|
+
Usage:
|
|
913
|
+
iterator<int, 16> Map; # Create 16-element iterator space
|
|
914
|
+
Map::iterator::set(0, 5); # Set iterator 0 to position 5
|
|
915
|
+
Map::iterator::task(0, myFunc); # Attach task to iterator
|
|
916
|
+
"""
|
|
917
|
+
|
|
918
|
+
def __init__(self, element_type: str = 'int', size: int = 16):
|
|
919
|
+
self._element_type = element_type
|
|
920
|
+
self._size = size
|
|
921
|
+
self._data: List[Any] = [None] * size
|
|
922
|
+
self._iterators: Dict[int, int] = {0: 0, 1: 1} # Default: 2 iterators at positions 0 and 1
|
|
923
|
+
self._tasks: Dict[int, Callable] = {}
|
|
924
|
+
|
|
925
|
+
def insert(self, index: int, value: Any) -> 'Iterator':
|
|
926
|
+
"""Insert value at index"""
|
|
927
|
+
if 0 <= index < self._size:
|
|
928
|
+
self._data[index] = value
|
|
929
|
+
return self
|
|
930
|
+
|
|
931
|
+
def fill(self, value: Any) -> 'Iterator':
|
|
932
|
+
"""Fill all positions with value"""
|
|
933
|
+
self._data = [value] * self._size
|
|
934
|
+
return self
|
|
935
|
+
|
|
936
|
+
def at(self, index: int) -> Any:
|
|
937
|
+
"""Get value at index"""
|
|
938
|
+
if 0 <= index < self._size:
|
|
939
|
+
return self._data[index]
|
|
940
|
+
return None
|
|
941
|
+
|
|
942
|
+
def is_all(self, check_value: bool) -> bool:
|
|
943
|
+
"""Check if all values are 1 (True) or 0 (False)"""
|
|
944
|
+
expected = 1 if check_value else 0
|
|
945
|
+
return all(v == expected for v in self._data if v is not None)
|
|
946
|
+
|
|
947
|
+
def end(self) -> int:
|
|
948
|
+
"""Return last index"""
|
|
949
|
+
return self._size - 1
|
|
950
|
+
|
|
951
|
+
class IteratorControl:
|
|
952
|
+
"""Static methods for iterator control"""
|
|
953
|
+
|
|
954
|
+
@staticmethod
|
|
955
|
+
def set(iterator_obj: 'Iterator', iterator_id: int, position: int):
|
|
956
|
+
"""Set iterator position"""
|
|
957
|
+
iterator_obj._iterators[iterator_id] = position
|
|
958
|
+
|
|
959
|
+
@staticmethod
|
|
960
|
+
def move(iterator_obj: 'Iterator', iterator_id: int, steps: int):
|
|
961
|
+
"""Move iterator by steps"""
|
|
962
|
+
if iterator_id in iterator_obj._iterators:
|
|
963
|
+
iterator_obj._iterators[iterator_id] += steps
|
|
964
|
+
|
|
965
|
+
@staticmethod
|
|
966
|
+
def insert(iterator_obj: 'Iterator', iterator_id: int, value: Any):
|
|
967
|
+
"""Insert value at current iterator position"""
|
|
968
|
+
if iterator_id in iterator_obj._iterators:
|
|
969
|
+
pos = iterator_obj._iterators[iterator_id]
|
|
970
|
+
if 0 <= pos < iterator_obj._size:
|
|
971
|
+
iterator_obj._data[pos] = value
|
|
972
|
+
|
|
973
|
+
@staticmethod
|
|
974
|
+
def pop(iterator_obj: 'Iterator', iterator_id: int):
|
|
975
|
+
"""Delete value at current iterator position"""
|
|
976
|
+
if iterator_id in iterator_obj._iterators:
|
|
977
|
+
pos = iterator_obj._iterators[iterator_id]
|
|
978
|
+
if 0 <= pos < iterator_obj._size:
|
|
979
|
+
iterator_obj._data[pos] = None
|
|
980
|
+
|
|
981
|
+
@staticmethod
|
|
982
|
+
def task(iterator_obj: 'Iterator', iterator_id: int, func: Callable):
|
|
983
|
+
"""Attach a task function to iterator"""
|
|
984
|
+
iterator_obj._tasks[iterator_id] = func
|
|
985
|
+
|
|
986
|
+
@staticmethod
|
|
987
|
+
def dtask(iterator_obj: 'Iterator', iterator_id: int):
|
|
988
|
+
"""Clear task from iterator"""
|
|
989
|
+
if iterator_id in iterator_obj._tasks:
|
|
990
|
+
del iterator_obj._tasks[iterator_id]
|
|
991
|
+
|
|
992
|
+
@staticmethod
|
|
993
|
+
def run_task(iterator_obj: 'Iterator', iterator_id: int):
|
|
994
|
+
"""Run the task at current iterator position"""
|
|
995
|
+
if iterator_id in iterator_obj._tasks and iterator_id in iterator_obj._iterators:
|
|
996
|
+
pos = iterator_obj._iterators[iterator_id]
|
|
997
|
+
task = iterator_obj._tasks[iterator_id]
|
|
998
|
+
# Create a position wrapper
|
|
999
|
+
class IteratorPos:
|
|
1000
|
+
def __init__(self, data, idx):
|
|
1001
|
+
self._data = data
|
|
1002
|
+
self._idx = idx
|
|
1003
|
+
def read(self):
|
|
1004
|
+
return self._data[self._idx]
|
|
1005
|
+
def write(self, value):
|
|
1006
|
+
self._data[self._idx] = value
|
|
1007
|
+
|
|
1008
|
+
task(IteratorPos(iterator_obj._data, pos))
|
|
1009
|
+
|
|
1010
|
+
|
|
1011
|
+
class Combo:
|
|
1012
|
+
"""Filter/search space for open parameter matching.
|
|
1013
|
+
|
|
1014
|
+
Creates a search/filter space that can match parameters
|
|
1015
|
+
based on filter databases and similarity.
|
|
1016
|
+
|
|
1017
|
+
Usage:
|
|
1018
|
+
combo<open&string> nameSpace;
|
|
1019
|
+
nameSpace +<== [combo::filterdb] filterDB;
|
|
1020
|
+
special_name = OpenFind(&nameSpace);
|
|
1021
|
+
"""
|
|
1022
|
+
|
|
1023
|
+
def __init__(self, element_type: str = 'dynamic'):
|
|
1024
|
+
self._element_type = element_type
|
|
1025
|
+
self._filterdb: List[Any] = []
|
|
1026
|
+
self._blocked: List[Any] = []
|
|
1027
|
+
self._data: List[Any] = []
|
|
1028
|
+
self._like_pattern: Optional[str] = None
|
|
1029
|
+
|
|
1030
|
+
@property
|
|
1031
|
+
def filterdb(self) -> List[Any]:
|
|
1032
|
+
return self._filterdb
|
|
1033
|
+
|
|
1034
|
+
@filterdb.setter
|
|
1035
|
+
def filterdb(self, value: List[Any]):
|
|
1036
|
+
self._filterdb = value
|
|
1037
|
+
|
|
1038
|
+
@property
|
|
1039
|
+
def blocked(self) -> List[Any]:
|
|
1040
|
+
return self._blocked
|
|
1041
|
+
|
|
1042
|
+
@blocked.setter
|
|
1043
|
+
def blocked(self, value: List[Any]):
|
|
1044
|
+
self._blocked = value
|
|
1045
|
+
|
|
1046
|
+
def like(self, pattern: str) -> 'Combo':
|
|
1047
|
+
"""Set similarity pattern (94-100% match)"""
|
|
1048
|
+
self._like_pattern = pattern
|
|
1049
|
+
return self
|
|
1050
|
+
|
|
1051
|
+
def matches(self, value: Any) -> bool:
|
|
1052
|
+
"""Check if value matches combo criteria"""
|
|
1053
|
+
# Check if blocked
|
|
1054
|
+
if value in self._blocked:
|
|
1055
|
+
return False
|
|
1056
|
+
|
|
1057
|
+
# Check filterdb if present
|
|
1058
|
+
if self._filterdb:
|
|
1059
|
+
if value not in self._filterdb:
|
|
1060
|
+
return False
|
|
1061
|
+
|
|
1062
|
+
# Check like pattern if present
|
|
1063
|
+
if self._like_pattern and isinstance(value, str):
|
|
1064
|
+
similarity = self._calculate_similarity(value, self._like_pattern)
|
|
1065
|
+
if similarity < 0.94:
|
|
1066
|
+
return False
|
|
1067
|
+
|
|
1068
|
+
return True
|
|
1069
|
+
|
|
1070
|
+
def _calculate_similarity(self, s1: str, s2: str) -> float:
|
|
1071
|
+
"""Calculate string similarity (simple Levenshtein-based)"""
|
|
1072
|
+
if s1 == s2:
|
|
1073
|
+
return 1.0
|
|
1074
|
+
if not s1 or not s2:
|
|
1075
|
+
return 0.0
|
|
1076
|
+
|
|
1077
|
+
# Simple character-based similarity
|
|
1078
|
+
s1_lower = s1.lower()
|
|
1079
|
+
s2_lower = s2.lower()
|
|
1080
|
+
|
|
1081
|
+
matching = sum(c1 == c2 for c1, c2 in zip(s1_lower, s2_lower))
|
|
1082
|
+
return matching / max(len(s1), len(s2))
|
|
1083
|
+
|
|
1084
|
+
def find_match(self, items: List[Any]) -> Optional[Any]:
|
|
1085
|
+
"""Find first matching item from list"""
|
|
1086
|
+
for item in items:
|
|
1087
|
+
if self.matches(item):
|
|
1088
|
+
return item
|
|
1089
|
+
return None
|
|
1090
|
+
|
|
1091
|
+
|
|
1092
|
+
class DataSpace(dict):
|
|
1093
|
+
"""SQL/data storage container for structured data.
|
|
1094
|
+
|
|
1095
|
+
Used for SQL table definitions and structured data storage.
|
|
1096
|
+
|
|
1097
|
+
Usage:
|
|
1098
|
+
dataspace<sql::table> table = { ... };
|
|
1099
|
+
@Sql.Structured(&table);
|
|
1100
|
+
"""
|
|
1101
|
+
|
|
1102
|
+
def __init__(self, space_type: str = 'dynamic'):
|
|
1103
|
+
super().__init__()
|
|
1104
|
+
self._space_type = space_type
|
|
1105
|
+
self._sections: Dict[str, Any] = {}
|
|
1106
|
+
|
|
1107
|
+
def content(self) -> dict:
|
|
1108
|
+
"""Return all content"""
|
|
1109
|
+
return dict(self)
|
|
1110
|
+
|
|
1111
|
+
def section(self, name: str, *types) -> 'DataSpace':
|
|
1112
|
+
"""Create a section with specified types"""
|
|
1113
|
+
self._sections[name] = {
|
|
1114
|
+
'types': types,
|
|
1115
|
+
'data': []
|
|
1116
|
+
}
|
|
1117
|
+
return self
|
|
1118
|
+
|
|
1119
|
+
|
|
1120
|
+
class OpenQuote:
|
|
1121
|
+
"""SQL openquote container for organized data handling.
|
|
1122
|
+
|
|
1123
|
+
Creates a datastruct together with sql::db.oqt() for easy
|
|
1124
|
+
data organization and retrieval.
|
|
1125
|
+
|
|
1126
|
+
Usage:
|
|
1127
|
+
openquote<datastruct<dynamic>&@sql::db.oqt(@db)> Queue;
|
|
1128
|
+
Queue.save("Section", "data1", "data2", 123);
|
|
1129
|
+
Queue.where(Section="value", KEY="match");
|
|
1130
|
+
"""
|
|
1131
|
+
|
|
1132
|
+
def __init__(self, db_reference: Any = None):
|
|
1133
|
+
self._data: List[Dict[str, Any]] = []
|
|
1134
|
+
self._db_ref = db_reference
|
|
1135
|
+
|
|
1136
|
+
def save(self, section: str, *values) -> 'OpenQuote':
|
|
1137
|
+
"""Save data to a section"""
|
|
1138
|
+
self._data.append({
|
|
1139
|
+
'section': section,
|
|
1140
|
+
'values': list(values)
|
|
1141
|
+
})
|
|
1142
|
+
return self
|
|
1143
|
+
|
|
1144
|
+
def where(self, **kwargs) -> Optional[Any]:
|
|
1145
|
+
"""Find data matching criteria"""
|
|
1146
|
+
for entry in self._data:
|
|
1147
|
+
if all(entry.get(k) == v or (k == 'Section' and entry.get('section') == v)
|
|
1148
|
+
for k, v in kwargs.items()):
|
|
1149
|
+
return entry
|
|
1150
|
+
return None
|
|
1151
|
+
|
|
1152
|
+
def all(self) -> List[Dict[str, Any]]:
|
|
1153
|
+
"""Return all data"""
|
|
1154
|
+
return self._data
|
|
1155
|
+
|
|
1156
|
+
|
|
1157
|
+
class Parameter:
|
|
1158
|
+
"""Parameter accessor for CSSL exec() arguments.
|
|
1159
|
+
|
|
1160
|
+
Provides access to arguments passed to CSSL.exec() via parameter.get(index).
|
|
1161
|
+
|
|
1162
|
+
Usage in CSSL:
|
|
1163
|
+
parameter.get(0) # Get first argument
|
|
1164
|
+
parameter.get(1) # Get second argument
|
|
1165
|
+
parameter.count() # Get total argument count
|
|
1166
|
+
parameter.all() # Get all arguments as list
|
|
1167
|
+
parameter.return(value) # Yield a return value (generator-like)
|
|
1168
|
+
parameter.returns() # Get all yielded return values
|
|
1169
|
+
"""
|
|
1170
|
+
|
|
1171
|
+
def __init__(self, args: List[Any] = None):
|
|
1172
|
+
self._args = args if args is not None else []
|
|
1173
|
+
self._returns: List[Any] = []
|
|
1174
|
+
|
|
1175
|
+
def get(self, index: int, default: Any = None) -> Any:
|
|
1176
|
+
"""Get argument at index, returns default if not found"""
|
|
1177
|
+
if 0 <= index < len(self._args):
|
|
1178
|
+
return self._args[index]
|
|
1179
|
+
return default
|
|
1180
|
+
|
|
1181
|
+
def count(self) -> int:
|
|
1182
|
+
"""Return total number of arguments"""
|
|
1183
|
+
return len(self._args)
|
|
1184
|
+
|
|
1185
|
+
def all(self) -> List[Any]:
|
|
1186
|
+
"""Return all arguments as a list"""
|
|
1187
|
+
return list(self._args)
|
|
1188
|
+
|
|
1189
|
+
def has(self, index: int) -> bool:
|
|
1190
|
+
"""Check if argument exists at index"""
|
|
1191
|
+
return 0 <= index < len(self._args)
|
|
1192
|
+
|
|
1193
|
+
# Using 'return_' to avoid Python keyword conflict
|
|
1194
|
+
def return_(self, value: Any) -> None:
|
|
1195
|
+
"""Yield a return value (generator-like behavior).
|
|
1196
|
+
|
|
1197
|
+
Multiple calls accumulate values that can be retrieved via returns().
|
|
1198
|
+
The CSSL runtime will collect these as the exec() return value.
|
|
1199
|
+
"""
|
|
1200
|
+
self._returns.append(value)
|
|
1201
|
+
|
|
1202
|
+
def returns(self) -> List[Any]:
|
|
1203
|
+
"""Get all yielded return values"""
|
|
1204
|
+
return list(self._returns)
|
|
1205
|
+
|
|
1206
|
+
def clear_returns(self) -> None:
|
|
1207
|
+
"""Clear all yielded return values"""
|
|
1208
|
+
self._returns.clear()
|
|
1209
|
+
|
|
1210
|
+
def has_returns(self) -> bool:
|
|
1211
|
+
"""Check if any values have been returned"""
|
|
1212
|
+
return len(self._returns) > 0
|
|
1213
|
+
|
|
1214
|
+
def __iter__(self):
|
|
1215
|
+
return iter(self._args)
|
|
1216
|
+
|
|
1217
|
+
def __len__(self):
|
|
1218
|
+
return len(self._args)
|
|
1219
|
+
|
|
1220
|
+
def __getitem__(self, index: int) -> Any:
|
|
1221
|
+
return self.get(index)
|
|
1222
|
+
|
|
1223
|
+
|
|
1224
|
+
def OpenFind(combo_or_type: Union[Combo, type], index: int = 0) -> Optional[Any]:
|
|
1225
|
+
"""Find open parameter by type or combo space.
|
|
1226
|
+
|
|
1227
|
+
Usage:
|
|
1228
|
+
string name = OpenFind<string>(0); # Find string at index 0
|
|
1229
|
+
string special = OpenFind(&@comboSpace); # Find by combo
|
|
1230
|
+
"""
|
|
1231
|
+
if isinstance(combo_or_type, Combo):
|
|
1232
|
+
# Find by combo space
|
|
1233
|
+
return combo_or_type.find_match([]) # Would need open params context
|
|
1234
|
+
elif isinstance(combo_or_type, type):
|
|
1235
|
+
# Find by type at index - needs open params context
|
|
1236
|
+
pass
|
|
1237
|
+
return None
|
|
1238
|
+
|
|
1239
|
+
|
|
1240
|
+
# Type factory functions for CSSL
|
|
1241
|
+
def create_datastruct(element_type: str = 'dynamic') -> DataStruct:
|
|
1242
|
+
return DataStruct(element_type)
|
|
1243
|
+
|
|
1244
|
+
def create_shuffled(element_type: str = 'dynamic') -> Shuffled:
|
|
1245
|
+
return Shuffled(element_type)
|
|
1246
|
+
|
|
1247
|
+
def create_iterator(element_type: str = 'int', size: int = 16) -> Iterator:
|
|
1248
|
+
return Iterator(element_type, size)
|
|
1249
|
+
|
|
1250
|
+
def create_combo(element_type: str = 'dynamic') -> Combo:
|
|
1251
|
+
return Combo(element_type)
|
|
1252
|
+
|
|
1253
|
+
def create_dataspace(space_type: str = 'dynamic') -> DataSpace:
|
|
1254
|
+
return DataSpace(space_type)
|
|
1255
|
+
|
|
1256
|
+
def create_openquote(db_ref: Any = None) -> OpenQuote:
|
|
1257
|
+
return OpenQuote(db_ref)
|
|
1258
|
+
|
|
1259
|
+
def create_stack(element_type: str = 'dynamic') -> Stack:
|
|
1260
|
+
return Stack(element_type)
|
|
1261
|
+
|
|
1262
|
+
def create_vector(element_type: str = 'dynamic') -> Vector:
|
|
1263
|
+
return Vector(element_type)
|
|
1264
|
+
|
|
1265
|
+
def create_parameter(args: List[Any] = None) -> Parameter:
|
|
1266
|
+
"""Create a Parameter object for accessing exec arguments"""
|
|
1267
|
+
return Parameter(args)
|
|
1268
|
+
|
|
1269
|
+
def create_array(element_type: str = 'dynamic') -> Array:
|
|
1270
|
+
"""Create an Array object"""
|
|
1271
|
+
return Array(element_type)
|
|
1272
|
+
|
|
1273
|
+
|
|
1274
|
+
def create_list(element_type: str = 'dynamic') -> List:
|
|
1275
|
+
"""Create a List object"""
|
|
1276
|
+
return List(element_type)
|
|
1277
|
+
|
|
1278
|
+
|
|
1279
|
+
def create_dictionary(key_type: str = 'dynamic', value_type: str = 'dynamic') -> Dictionary:
|
|
1280
|
+
"""Create a Dictionary object"""
|
|
1281
|
+
return Dictionary(key_type, value_type)
|
|
1282
|
+
|
|
1283
|
+
|
|
1284
|
+
class Map(dict):
|
|
1285
|
+
"""C++ style map container with ordered key-value pairs.
|
|
1286
|
+
|
|
1287
|
+
Similar to Dictionary but with C++ map semantics.
|
|
1288
|
+
Keys are maintained in sorted order.
|
|
1289
|
+
|
|
1290
|
+
Usage:
|
|
1291
|
+
map<string, int> ages;
|
|
1292
|
+
ages.insert("Alice", 30);
|
|
1293
|
+
ages.find("Alice");
|
|
1294
|
+
ages.erase("Alice");
|
|
1295
|
+
"""
|
|
1296
|
+
|
|
1297
|
+
def __init__(self, key_type: str = 'dynamic', value_type: str = 'dynamic'):
|
|
1298
|
+
super().__init__()
|
|
1299
|
+
self._key_type = key_type
|
|
1300
|
+
self._value_type = value_type
|
|
1301
|
+
|
|
1302
|
+
def insert(self, key: Any, value: Any) -> 'Map':
|
|
1303
|
+
"""Insert key-value pair (C++ style)"""
|
|
1304
|
+
self[key] = value
|
|
1305
|
+
return self
|
|
1306
|
+
|
|
1307
|
+
def find(self, key: Any) -> Optional[Any]:
|
|
1308
|
+
"""Find value by key, returns None if not found (C++ style)"""
|
|
1309
|
+
return self.get(key, None)
|
|
1310
|
+
|
|
1311
|
+
def erase(self, key: Any) -> bool:
|
|
1312
|
+
"""Erase key-value pair, returns True if existed"""
|
|
1313
|
+
if key in self:
|
|
1314
|
+
del self[key]
|
|
1315
|
+
return True
|
|
1316
|
+
return False
|
|
1317
|
+
|
|
1318
|
+
def contains(self, key: Any) -> bool:
|
|
1319
|
+
"""Check if key exists (C++20 style)"""
|
|
1320
|
+
return key in self
|
|
1321
|
+
|
|
1322
|
+
def count(self, key: Any) -> int:
|
|
1323
|
+
"""Return 1 if key exists, 0 otherwise (C++ style)"""
|
|
1324
|
+
return 1 if key in self else 0
|
|
1325
|
+
|
|
1326
|
+
def size(self) -> int:
|
|
1327
|
+
"""Return map size"""
|
|
1328
|
+
return len(self)
|
|
1329
|
+
|
|
1330
|
+
def empty(self) -> bool:
|
|
1331
|
+
"""Check if map is empty"""
|
|
1332
|
+
return len(self) == 0
|
|
1333
|
+
|
|
1334
|
+
def at(self, key: Any) -> Any:
|
|
1335
|
+
"""Get value at key, raises error if not found (C++ style)"""
|
|
1336
|
+
if key not in self:
|
|
1337
|
+
raise KeyError(f"Key '{key}' not found in map")
|
|
1338
|
+
return self[key]
|
|
1339
|
+
|
|
1340
|
+
def begin(self) -> Optional[tuple]:
|
|
1341
|
+
"""Return first key-value pair"""
|
|
1342
|
+
if len(self) == 0:
|
|
1343
|
+
return None
|
|
1344
|
+
first_key = next(iter(self))
|
|
1345
|
+
return (first_key, self[first_key])
|
|
1346
|
+
|
|
1347
|
+
def end(self) -> Optional[tuple]:
|
|
1348
|
+
"""Return last key-value pair"""
|
|
1349
|
+
if len(self) == 0:
|
|
1350
|
+
return None
|
|
1351
|
+
last_key = list(self.keys())[-1]
|
|
1352
|
+
return (last_key, self[last_key])
|
|
1353
|
+
|
|
1354
|
+
def lower_bound(self, key: Any) -> Optional[Any]:
|
|
1355
|
+
"""Find first key >= given key (for sorted keys)"""
|
|
1356
|
+
sorted_keys = sorted(self.keys())
|
|
1357
|
+
for k in sorted_keys:
|
|
1358
|
+
if k >= key:
|
|
1359
|
+
return k
|
|
1360
|
+
return None
|
|
1361
|
+
|
|
1362
|
+
def upper_bound(self, key: Any) -> Optional[Any]:
|
|
1363
|
+
"""Find first key > given key (for sorted keys)"""
|
|
1364
|
+
sorted_keys = sorted(self.keys())
|
|
1365
|
+
for k in sorted_keys:
|
|
1366
|
+
if k > key:
|
|
1367
|
+
return k
|
|
1368
|
+
return None
|
|
1369
|
+
|
|
1370
|
+
|
|
1371
|
+
def create_map(key_type: str = 'dynamic', value_type: str = 'dynamic') -> Map:
|
|
1372
|
+
"""Create a Map object"""
|
|
1373
|
+
return Map(key_type, value_type)
|
|
1374
|
+
|
|
1375
|
+
|
|
1376
|
+
class CSSLClass:
|
|
1377
|
+
"""Represents a CSSL class definition.
|
|
1378
|
+
|
|
1379
|
+
Stores class name, member variables, methods, and constructor.
|
|
1380
|
+
Used by the runtime to instantiate CSSLInstance objects.
|
|
1381
|
+
"""
|
|
1382
|
+
|
|
1383
|
+
def __init__(self, name: str, members: Dict[str, Any] = None,
|
|
1384
|
+
methods: Dict[str, Any] = None, constructor: Any = None):
|
|
1385
|
+
self.name = name
|
|
1386
|
+
self.members = members or {} # Default member values/types
|
|
1387
|
+
self.methods = methods or {} # Method AST nodes
|
|
1388
|
+
self.constructor = constructor # Constructor AST node
|
|
1389
|
+
|
|
1390
|
+
def __repr__(self):
|
|
1391
|
+
return f"<CSSLClass '{self.name}' with {len(self.methods)} methods>"
|
|
1392
|
+
|
|
1393
|
+
|
|
1394
|
+
class CSSLInstance:
|
|
1395
|
+
"""Represents an instance of a CSSL class.
|
|
1396
|
+
|
|
1397
|
+
Holds instance member values and provides access to class methods.
|
|
1398
|
+
Supports this-> member access pattern.
|
|
1399
|
+
"""
|
|
1400
|
+
|
|
1401
|
+
def __init__(self, class_def: CSSLClass):
|
|
1402
|
+
self._class = class_def
|
|
1403
|
+
self._members: Dict[str, Any] = {}
|
|
1404
|
+
# Initialize members with defaults from class definition
|
|
1405
|
+
for name, default in class_def.members.items():
|
|
1406
|
+
if isinstance(default, dict):
|
|
1407
|
+
# Type declaration with optional default
|
|
1408
|
+
member_type = default.get('type')
|
|
1409
|
+
member_default = default.get('default')
|
|
1410
|
+
|
|
1411
|
+
if member_default is not None:
|
|
1412
|
+
self._members[name] = member_default
|
|
1413
|
+
elif member_type:
|
|
1414
|
+
# Create instance of container types
|
|
1415
|
+
self._members[name] = self._create_default_for_type(member_type)
|
|
1416
|
+
else:
|
|
1417
|
+
self._members[name] = None
|
|
1418
|
+
else:
|
|
1419
|
+
self._members[name] = default
|
|
1420
|
+
|
|
1421
|
+
def _create_default_for_type(self, type_name: str) -> Any:
|
|
1422
|
+
"""Create a default value for a given type name."""
|
|
1423
|
+
# Container types
|
|
1424
|
+
if type_name == 'map':
|
|
1425
|
+
return Map()
|
|
1426
|
+
elif type_name in ('stack',):
|
|
1427
|
+
return Stack()
|
|
1428
|
+
elif type_name in ('vector',):
|
|
1429
|
+
return Vector()
|
|
1430
|
+
elif type_name in ('array',):
|
|
1431
|
+
return Array()
|
|
1432
|
+
elif type_name in ('list',):
|
|
1433
|
+
return List()
|
|
1434
|
+
elif type_name in ('dictionary', 'dict'):
|
|
1435
|
+
return Dictionary()
|
|
1436
|
+
elif type_name == 'datastruct':
|
|
1437
|
+
return DataStruct()
|
|
1438
|
+
elif type_name == 'dataspace':
|
|
1439
|
+
return DataSpace()
|
|
1440
|
+
elif type_name == 'shuffled':
|
|
1441
|
+
return Shuffled()
|
|
1442
|
+
elif type_name == 'iterator':
|
|
1443
|
+
return Iterator()
|
|
1444
|
+
elif type_name == 'combo':
|
|
1445
|
+
return Combo()
|
|
1446
|
+
# Primitive types
|
|
1447
|
+
elif type_name == 'int':
|
|
1448
|
+
return 0
|
|
1449
|
+
elif type_name == 'float':
|
|
1450
|
+
return 0.0
|
|
1451
|
+
elif type_name == 'string':
|
|
1452
|
+
return ""
|
|
1453
|
+
elif type_name == 'bool':
|
|
1454
|
+
return False
|
|
1455
|
+
elif type_name == 'json':
|
|
1456
|
+
return {}
|
|
1457
|
+
return None
|
|
1458
|
+
|
|
1459
|
+
def get_member(self, name: str) -> Any:
|
|
1460
|
+
"""Get member value by name"""
|
|
1461
|
+
if name in self._members:
|
|
1462
|
+
return self._members[name]
|
|
1463
|
+
raise AttributeError(f"'{self._class.name}' has no member '{name}'")
|
|
1464
|
+
|
|
1465
|
+
def set_member(self, name: str, value: Any) -> None:
|
|
1466
|
+
"""Set member value by name"""
|
|
1467
|
+
self._members[name] = value
|
|
1468
|
+
|
|
1469
|
+
def has_member(self, name: str) -> bool:
|
|
1470
|
+
"""Check if member exists"""
|
|
1471
|
+
return name in self._members
|
|
1472
|
+
|
|
1473
|
+
def get_method(self, name: str) -> Any:
|
|
1474
|
+
"""Get method AST node by name"""
|
|
1475
|
+
if name in self._class.methods:
|
|
1476
|
+
return self._class.methods[name]
|
|
1477
|
+
raise AttributeError(f"'{self._class.name}' has no method '{name}'")
|
|
1478
|
+
|
|
1479
|
+
def has_method(self, name: str) -> bool:
|
|
1480
|
+
"""Check if method exists"""
|
|
1481
|
+
return name in self._class.methods
|
|
1482
|
+
|
|
1483
|
+
def __getattr__(self, name: str) -> Any:
|
|
1484
|
+
"""Allow direct attribute access for members"""
|
|
1485
|
+
if name.startswith('_'):
|
|
1486
|
+
raise AttributeError(name)
|
|
1487
|
+
if name in self._members:
|
|
1488
|
+
return self._members[name]
|
|
1489
|
+
raise AttributeError(f"'{self._class.name}' has no member '{name}'")
|
|
1490
|
+
|
|
1491
|
+
def __setattr__(self, name: str, value: Any) -> None:
|
|
1492
|
+
"""Allow direct attribute setting for members"""
|
|
1493
|
+
if name.startswith('_'):
|
|
1494
|
+
object.__setattr__(self, name, value)
|
|
1495
|
+
else:
|
|
1496
|
+
if hasattr(self, '_members'):
|
|
1497
|
+
self._members[name] = value
|
|
1498
|
+
else:
|
|
1499
|
+
object.__setattr__(self, name, value)
|
|
1500
|
+
|
|
1501
|
+
def __repr__(self):
|
|
1502
|
+
return f"<CSSLInstance of '{self._class.name}'>"
|
|
1503
|
+
|
|
1504
|
+
|
|
1505
|
+
__all__ = [
|
|
1506
|
+
'DataStruct', 'Shuffled', 'Iterator', 'Combo', 'DataSpace', 'OpenQuote',
|
|
1507
|
+
'OpenFind', 'Parameter', 'Stack', 'Vector', 'Array', 'List', 'Dictionary', 'Map',
|
|
1508
|
+
'CSSLClass', 'CSSLInstance',
|
|
1509
|
+
'create_datastruct', 'create_shuffled', 'create_iterator',
|
|
1510
|
+
'create_combo', 'create_dataspace', 'create_openquote', 'create_parameter',
|
|
1511
|
+
'create_stack', 'create_vector', 'create_array', 'create_list', 'create_dictionary', 'create_map'
|
|
1512
|
+
]
|