obstruct 0.6.0__tar.gz → 0.6.2__tar.gz
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.
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/workspace.xml +106 -48
- {obstruct-0.6.0 → obstruct-0.6.2}/PKG-INFO +1 -1
- obstruct-0.6.2/src/obstruct/__version__.py +1 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/base.py +39 -4
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/field.py +5 -5
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/pack.py +2 -2
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/schema.py +4 -1
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/unpack.py +62 -27
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/schema_methods.py +10 -0
- obstruct-0.6.2/test/test_new.py +53 -0
- obstruct-0.6.2/test/test_s_and_x.py +52 -0
- obstruct-0.6.2/test/test_str_field.py +21 -0
- obstruct-0.6.2/v0.5.2-speed-log.log +137 -0
- obstruct-0.6.0/src/obstruct/__version__.py +0 -1
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/.gitignore +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/inspectionProfiles/Project_Default.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/inspectionProfiles/profiles_settings.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/misc.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/modules.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/obstruct.iml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/shelf/_2026_9_6_14_40____.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/shelf//345/234/250/350/277/233/350/241/214/346/233/264/346/226/260/344/271/213/345/211/215/344/272/216_2026_9_6_14_40_/345/217/226/346/266/210/346/217/220/344/272/244/344/272/206/346/233/264/346/224/271_[/346/233/264/346/224/271]/shelved.patch" +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/.idea/vcs.xml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/BENCHMARK_TEST-v0.5.0.md +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/BENCHMARK_TEST-v0.6.0.md +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/LICENSE +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/README.md +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/USAGE.md +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/pyproject.toml +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/__init__.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/__init__.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/aot/aot.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/methods.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/struct_type.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/types/__init__.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/types/types.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/src/obstruct/types/types.pyi +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test/test.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test/test_gen_from_schema.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test/test_speed.py +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test-unsafe-new.log +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test.log +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test1.log +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/test2.log +0 -0
- {obstruct-0.6.0 → obstruct-0.6.2}/uv.lock +0 -0
|
@@ -4,29 +4,13 @@
|
|
|
4
4
|
<option name="autoReloadType" value="SELECTIVE" />
|
|
5
5
|
</component>
|
|
6
6
|
<component name="ChangeListManager">
|
|
7
|
-
<list default="true" id="b482b6b4-48ce-4be1-bf3c-a72ec254fa35" name="更改" comment="fix:
|
|
8
|
-
<change afterPath="$PROJECT_DIR$/
|
|
9
|
-
<change afterPath="$PROJECT_DIR$/USAGE.md" afterDir="false" />
|
|
10
|
-
<change afterPath="$PROJECT_DIR$/src/obstruct/aot/field.py" afterDir="false" />
|
|
11
|
-
<change afterPath="$PROJECT_DIR$/src/obstruct/aot/schema.py" afterDir="false" />
|
|
12
|
-
<change afterPath="$PROJECT_DIR$/src/obstruct/schema_methods.py" afterDir="false" />
|
|
13
|
-
<change beforePath="$PROJECT_DIR$/BENCHMARK_TEST.md" beforeDir="false" afterPath="$PROJECT_DIR$/BENCHMARK_TEST-v0.5.0.md" afterDir="false" />
|
|
14
|
-
<change beforePath="$PROJECT_DIR$/README.md" beforeDir="false" afterPath="$PROJECT_DIR$/README.md" afterDir="false" />
|
|
15
|
-
<change beforePath="$PROJECT_DIR$/pyproject.toml" beforeDir="false" afterPath="$PROJECT_DIR$/pyproject.toml" afterDir="false" />
|
|
16
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/__init__.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/__init__.py" afterDir="false" />
|
|
17
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/__init__.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/__init__.py" afterDir="false" />
|
|
18
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/aot.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/aot.py" afterDir="false" />
|
|
7
|
+
<list default="true" id="b482b6b4-48ce-4be1-bf3c-a72ec254fa35" name="更改" comment="fix: 未删除的调试语句 + update version to 0.6.1">
|
|
8
|
+
<change afterPath="$PROJECT_DIR$/test/test_str_field.py" afterDir="false" />
|
|
19
9
|
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/base.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/base.py" afterDir="false" />
|
|
20
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/
|
|
10
|
+
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/field.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/field.py" afterDir="false" />
|
|
11
|
+
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/schema.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/schema.py" afterDir="false" />
|
|
21
12
|
<change beforePath="$PROJECT_DIR$/src/obstruct/aot/unpack.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/aot/unpack.py" afterDir="false" />
|
|
22
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/
|
|
23
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/methods.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/methods.py" afterDir="false" />
|
|
24
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/struct_type.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/struct_type.py" afterDir="false" />
|
|
25
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/types/__init__.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/types/__init__.py" afterDir="false" />
|
|
26
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/types/base.py" beforeDir="false" />
|
|
27
|
-
<change beforePath="$PROJECT_DIR$/src/obstruct/types/types.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/types/types.py" afterDir="false" />
|
|
28
|
-
<change beforePath="$PROJECT_DIR$/test/test_speed.py" beforeDir="false" afterPath="$PROJECT_DIR$/test/test_speed.py" afterDir="false" />
|
|
29
|
-
<change beforePath="$PROJECT_DIR$/uv.lock" beforeDir="false" afterPath="$PROJECT_DIR$/uv.lock" afterDir="false" />
|
|
13
|
+
<change beforePath="$PROJECT_DIR$/src/obstruct/schema_methods.py" beforeDir="false" afterPath="$PROJECT_DIR$/src/obstruct/schema_methods.py" afterDir="false" />
|
|
30
14
|
</list>
|
|
31
15
|
<option name="SHOW_DIALOG" value="false" />
|
|
32
16
|
<option name="HIGHLIGHT_CONFLICTS" value="true" />
|
|
@@ -41,6 +25,11 @@
|
|
|
41
25
|
</option>
|
|
42
26
|
</component>
|
|
43
27
|
<component name="Git.Settings">
|
|
28
|
+
<option name="RECENT_BRANCH_BY_REPOSITORY">
|
|
29
|
+
<map>
|
|
30
|
+
<entry key="$PROJECT_DIR$" value="cce909ac291c4d0b7cb243ecf0dc4845dd8cc422" />
|
|
31
|
+
</map>
|
|
32
|
+
</option>
|
|
44
33
|
<option name="RECENT_GIT_ROOT_PATH" value="$PROJECT_DIR$" />
|
|
45
34
|
</component>
|
|
46
35
|
<component name="GitHubPullRequestSearchHistory">{
|
|
@@ -64,35 +53,38 @@
|
|
|
64
53
|
<option name="hideEmptyMiddlePackages" value="true" />
|
|
65
54
|
<option name="showLibraryContents" value="true" />
|
|
66
55
|
</component>
|
|
67
|
-
<component name="PropertiesComponent"
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
56
|
+
<component name="PropertiesComponent"><![CDATA[{
|
|
57
|
+
"keyToString": {
|
|
58
|
+
"ModuleVcsDetector.initialDetectionPerformed": "true",
|
|
59
|
+
"Python.test.executor": "Run",
|
|
60
|
+
"Python.test_gen_from_schema.executor": "Run",
|
|
61
|
+
"Python.test_new.executor": "Run",
|
|
62
|
+
"Python.test_s_and_x.executor": "Run",
|
|
63
|
+
"Python.test_speed.executor": "Run",
|
|
64
|
+
"Python.test_str_field.executor": "Run",
|
|
65
|
+
"RunOnceActivity.ShowReadmeOnStart": "true",
|
|
66
|
+
"RunOnceActivity.git.unshallow": "true",
|
|
67
|
+
"RunOnceActivity.typescript.service.memoryLimit.init": "true",
|
|
68
|
+
"codeWithMe.voiceChat.enabledByDefault": "false",
|
|
69
|
+
"git-widget-placeholder": "main",
|
|
70
|
+
"last_opened_file_path": "E:/.projects/obstruct",
|
|
71
|
+
"node.js.detected.package.eslint": "true",
|
|
72
|
+
"node.js.detected.package.jshint": "true",
|
|
73
|
+
"node.js.detected.package.tslint": "true",
|
|
74
|
+
"node.js.selected.package.eslint": "(autodetect)",
|
|
75
|
+
"node.js.selected.package.jshint": "",
|
|
76
|
+
"node.js.selected.package.tslint": "(autodetect)",
|
|
77
|
+
"nodejs_package_manager_path": "npm",
|
|
78
|
+
"settings.editor.selected.configurable": "editing.templates"
|
|
87
79
|
}
|
|
88
|
-
}
|
|
80
|
+
}]]></component>
|
|
89
81
|
<component name="RecentsManager">
|
|
90
82
|
<key name="MoveFile.RECENT_KEYS">
|
|
91
83
|
<recent name="E:\.projects\obstruct\src\obstruct" />
|
|
92
84
|
<recent name="E:\.projects\obstruct\src\obstruct\aot" />
|
|
93
85
|
</key>
|
|
94
86
|
</component>
|
|
95
|
-
<component name="RunManager" selected="Python.
|
|
87
|
+
<component name="RunManager" selected="Python.test_str_field">
|
|
96
88
|
<configuration name="test" type="PythonConfigurationType" factoryName="Python" temporary="true" nameIsGenerated="true">
|
|
97
89
|
<module name="obstruct" />
|
|
98
90
|
<option name="ENV_FILES" value="" />
|
|
@@ -151,6 +143,30 @@
|
|
|
151
143
|
<option name="INPUT_FILE" value="" />
|
|
152
144
|
<method v="2" />
|
|
153
145
|
</configuration>
|
|
146
|
+
<configuration name="test_s_and_x" type="PythonConfigurationType" factoryName="Python" temporary="true" nameIsGenerated="true">
|
|
147
|
+
<module name="obstruct" />
|
|
148
|
+
<option name="ENV_FILES" value="" />
|
|
149
|
+
<option name="INTERPRETER_OPTIONS" value="" />
|
|
150
|
+
<option name="PARENT_ENVS" value="true" />
|
|
151
|
+
<envs>
|
|
152
|
+
<env name="PYTHONUNBUFFERED" value="1" />
|
|
153
|
+
</envs>
|
|
154
|
+
<option name="SDK_HOME" value="" />
|
|
155
|
+
<option name="WORKING_DIRECTORY" value="$PROJECT_DIR$/test" />
|
|
156
|
+
<option name="IS_MODULE_SDK" value="true" />
|
|
157
|
+
<option name="ADD_CONTENT_ROOTS" value="true" />
|
|
158
|
+
<option name="ADD_SOURCE_ROOTS" value="true" />
|
|
159
|
+
<option name="DEBUG_JUST_MY_CODE" value="false" />
|
|
160
|
+
<option name="RUN_TOOL" value="" />
|
|
161
|
+
<option name="SCRIPT_NAME" value="$PROJECT_DIR$/test/test_s_and_x.py" />
|
|
162
|
+
<option name="PARAMETERS" value="" />
|
|
163
|
+
<option name="SHOW_COMMAND_LINE" value="false" />
|
|
164
|
+
<option name="EMULATE_TERMINAL" value="false" />
|
|
165
|
+
<option name="MODULE_MODE" value="false" />
|
|
166
|
+
<option name="REDIRECT_INPUT" value="false" />
|
|
167
|
+
<option name="INPUT_FILE" value="" />
|
|
168
|
+
<method v="2" />
|
|
169
|
+
</configuration>
|
|
154
170
|
<configuration name="test_speed" type="PythonConfigurationType" factoryName="Python" temporary="true" nameIsGenerated="true">
|
|
155
171
|
<module name="obstruct" />
|
|
156
172
|
<option name="ENV_FILES" value="" />
|
|
@@ -175,11 +191,37 @@
|
|
|
175
191
|
<option name="INPUT_FILE" value="" />
|
|
176
192
|
<method v="2" />
|
|
177
193
|
</configuration>
|
|
194
|
+
<configuration name="test_str_field" type="PythonConfigurationType" factoryName="Python" temporary="true" nameIsGenerated="true">
|
|
195
|
+
<module name="obstruct" />
|
|
196
|
+
<option name="ENV_FILES" value="" />
|
|
197
|
+
<option name="INTERPRETER_OPTIONS" value="" />
|
|
198
|
+
<option name="PARENT_ENVS" value="true" />
|
|
199
|
+
<envs>
|
|
200
|
+
<env name="PYTHONUNBUFFERED" value="1" />
|
|
201
|
+
</envs>
|
|
202
|
+
<option name="SDK_HOME" value="" />
|
|
203
|
+
<option name="WORKING_DIRECTORY" value="$PROJECT_DIR$/test" />
|
|
204
|
+
<option name="IS_MODULE_SDK" value="true" />
|
|
205
|
+
<option name="ADD_CONTENT_ROOTS" value="true" />
|
|
206
|
+
<option name="ADD_SOURCE_ROOTS" value="true" />
|
|
207
|
+
<option name="DEBUG_JUST_MY_CODE" value="false" />
|
|
208
|
+
<option name="RUN_TOOL" value="" />
|
|
209
|
+
<option name="SCRIPT_NAME" value="$PROJECT_DIR$/test/test_str_field.py" />
|
|
210
|
+
<option name="PARAMETERS" value="" />
|
|
211
|
+
<option name="SHOW_COMMAND_LINE" value="false" />
|
|
212
|
+
<option name="EMULATE_TERMINAL" value="false" />
|
|
213
|
+
<option name="MODULE_MODE" value="false" />
|
|
214
|
+
<option name="REDIRECT_INPUT" value="false" />
|
|
215
|
+
<option name="INPUT_FILE" value="" />
|
|
216
|
+
<method v="2" />
|
|
217
|
+
</configuration>
|
|
178
218
|
<recent_temporary>
|
|
179
219
|
<list>
|
|
180
|
-
<item itemvalue="Python.
|
|
220
|
+
<item itemvalue="Python.test_str_field" />
|
|
221
|
+
<item itemvalue="Python.test_s_and_x" />
|
|
181
222
|
<item itemvalue="Python.test_speed" />
|
|
182
223
|
<item itemvalue="Python.test_gen_from_schema" />
|
|
224
|
+
<item itemvalue="Python.test" />
|
|
183
225
|
</list>
|
|
184
226
|
</recent_temporary>
|
|
185
227
|
</component>
|
|
@@ -414,7 +456,23 @@
|
|
|
414
456
|
<option name="project" value="LOCAL" />
|
|
415
457
|
<updated>1787044545927</updated>
|
|
416
458
|
</task>
|
|
417
|
-
<
|
|
459
|
+
<task id="LOCAL-00028" summary="refactor: 优化数组和复杂结构体的解析性能,将 AOT 重写数据驱动 + update version to 0.6.0 + 更新测速脚本,添加新的性能测试信息 + 更新 README.md - 移除了旧的 metadata_marks.py,全面转向新的 Meta 元数据类型">
|
|
460
|
+
<option name="closed" value="true" />
|
|
461
|
+
<created>1788678016647</created>
|
|
462
|
+
<option name="number" value="00028" />
|
|
463
|
+
<option name="presentableId" value="LOCAL-00028" />
|
|
464
|
+
<option name="project" value="LOCAL" />
|
|
465
|
+
<updated>1788678016647</updated>
|
|
466
|
+
</task>
|
|
467
|
+
<task id="LOCAL-00029" summary="fix: 未删除的调试语句 + update version to 0.6.1">
|
|
468
|
+
<option name="closed" value="true" />
|
|
469
|
+
<created>1788678088267</created>
|
|
470
|
+
<option name="number" value="00029" />
|
|
471
|
+
<option name="presentableId" value="LOCAL-00029" />
|
|
472
|
+
<option name="project" value="LOCAL" />
|
|
473
|
+
<updated>1788678088267</updated>
|
|
474
|
+
</task>
|
|
475
|
+
<option name="localTasksCounter" value="30" />
|
|
418
476
|
<servers />
|
|
419
477
|
</component>
|
|
420
478
|
<component name="TypeScriptGeneratedFilesManager">
|
|
@@ -432,8 +490,6 @@
|
|
|
432
490
|
</option>
|
|
433
491
|
</component>
|
|
434
492
|
<component name="VcsManagerConfiguration">
|
|
435
|
-
<MESSAGE value="增强类型系统,撰写 README.md" />
|
|
436
|
-
<MESSAGE value="补充:基准测试脚本" />
|
|
437
493
|
<MESSAGE value="修正了一些命名" />
|
|
438
494
|
<MESSAGE value="增强 array 类型的支持" />
|
|
439
495
|
<MESSAGE value="增强 array 类型的支持 x2" />
|
|
@@ -457,6 +513,8 @@
|
|
|
457
513
|
<MESSAGE value="fix: 未删除的调试语句" />
|
|
458
514
|
<MESSAGE value="fix: 未删除的调试语句 + version: 0.5.1" />
|
|
459
515
|
<MESSAGE value="fix: 错误的别名 + version: 0.5.2" />
|
|
460
|
-
<
|
|
516
|
+
<MESSAGE value="refactor: 优化数组和复杂结构体的解析性能,将 AOT 重写数据驱动 + update version to 0.6.0 + 更新测速脚本,添加新的性能测试信息 + 更新 README.md - 移除了旧的 metadata_marks.py,全面转向新的 Meta 元数据类型" />
|
|
517
|
+
<MESSAGE value="fix: 未删除的调试语句 + update version to 0.6.1" />
|
|
518
|
+
<option name="LAST_COMMIT_MESSAGE" value="fix: 未删除的调试语句 + update version to 0.6.1" />
|
|
461
519
|
</component>
|
|
462
520
|
</project>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
version = "0.6.2"
|
|
@@ -106,10 +106,45 @@ class for_stmt(_objective_node_operator):
|
|
|
106
106
|
|
|
107
107
|
|
|
108
108
|
def name_generator(prefix='var_'):
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
109
|
+
return NameGenerator(prefix=prefix)
|
|
110
|
+
|
|
111
|
+
|
|
112
|
+
class NameGenerator:
|
|
113
|
+
__slots__ = ['_prefix', '_cnt']
|
|
114
|
+
|
|
115
|
+
def __init__(self, prefix='var_'):
|
|
116
|
+
self._prefix = prefix
|
|
117
|
+
self._cnt = 0
|
|
118
|
+
|
|
119
|
+
@property
|
|
120
|
+
def prefix(self):
|
|
121
|
+
return self._prefix
|
|
122
|
+
|
|
123
|
+
@property
|
|
124
|
+
def cnt(self):
|
|
125
|
+
return self._cnt
|
|
126
|
+
|
|
127
|
+
def next(self):
|
|
128
|
+
self._cnt += 1
|
|
129
|
+
return f'{self._prefix}{self._cnt}'
|
|
130
|
+
|
|
131
|
+
def peek(self):
|
|
132
|
+
return f'{self._prefix}{self._cnt + 1}'
|
|
133
|
+
|
|
134
|
+
def pop(self):
|
|
135
|
+
self._cnt -= 1
|
|
136
|
+
|
|
137
|
+
def new(self):
|
|
138
|
+
return self.next()
|
|
139
|
+
|
|
140
|
+
def __call__(self):
|
|
141
|
+
return self.next()
|
|
142
|
+
|
|
143
|
+
def __next__(self):
|
|
144
|
+
return self.next()
|
|
145
|
+
|
|
146
|
+
def __iter__(self):
|
|
147
|
+
return self
|
|
113
148
|
|
|
114
149
|
|
|
115
150
|
def to_tuple_expression(names, prefix='self.'):
|
|
@@ -10,17 +10,17 @@ class Meta:
|
|
|
10
10
|
# 基本控制标志
|
|
11
11
|
not_a_field: bool = False
|
|
12
12
|
|
|
13
|
-
#
|
|
14
|
-
encoding: str =
|
|
13
|
+
# 针对字符串的控制参数
|
|
14
|
+
encoding: str | None = None
|
|
15
15
|
|
|
16
|
-
#
|
|
16
|
+
# 针对字节串的控制参数
|
|
17
17
|
trunc_nul: bool = False
|
|
18
18
|
|
|
19
|
-
#
|
|
19
|
+
# 针对数组类型的控制参数
|
|
20
20
|
len: int = 0
|
|
21
21
|
dtype: typing.Any = None
|
|
22
22
|
|
|
23
|
-
#
|
|
23
|
+
# 针对结构体类型的控制参数
|
|
24
24
|
unsafe_create: bool = False
|
|
25
25
|
|
|
26
26
|
|
|
@@ -66,8 +66,8 @@ def create_pack_methods(schema: StructType):
|
|
|
66
66
|
|
|
67
67
|
# pack.add_return(f"_pack({expression})")
|
|
68
68
|
|
|
69
|
-
print("Pack\n", pack.generate_code(), sep='', end='\n\n') # Debug
|
|
70
|
-
print("Pack Into\n", pack_into.generate_code(), sep='', end='\n\n') # Debug
|
|
69
|
+
# print("Pack\n", pack.generate_code(), sep='', end='\n\n') # Debug
|
|
70
|
+
# print("Pack Into\n", pack_into.generate_code(), sep='', end='\n\n') # Debug
|
|
71
71
|
|
|
72
72
|
format = schema.full_format_string
|
|
73
73
|
# print("Final Struct Format string:", format)
|
|
@@ -71,7 +71,6 @@ class BasicType:
|
|
|
71
71
|
from obstruct.types import force_endian
|
|
72
72
|
return struct.calcsize(force_endian(self.format_string, endian='native'))
|
|
73
73
|
|
|
74
|
-
|
|
75
74
|
@dataclass(slots=True)
|
|
76
75
|
class ArrayType:
|
|
77
76
|
dtype: str
|
|
@@ -96,5 +95,9 @@ class ArrayType:
|
|
|
96
95
|
def format_string(self):
|
|
97
96
|
return f'{self.size}s'
|
|
98
97
|
|
|
98
|
+
@property
|
|
99
|
+
def padmode_format_string(self):
|
|
100
|
+
return f'{self.size}x'
|
|
101
|
+
|
|
99
102
|
|
|
100
103
|
SchemaTypes = StructType | UnionType | BasicType | ArrayType
|
|
@@ -6,8 +6,8 @@ import struct
|
|
|
6
6
|
import typing
|
|
7
7
|
|
|
8
8
|
from .base import name_generator, function_def, for_stmt
|
|
9
|
-
from .schema import StructType, ArrayType, BasicType
|
|
10
9
|
from .field import Meta
|
|
10
|
+
from .schema import StructType, ArrayType, BasicType
|
|
11
11
|
|
|
12
12
|
if typing.TYPE_CHECKING:
|
|
13
13
|
pass
|
|
@@ -57,44 +57,49 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
57
57
|
|
|
58
58
|
array_fields = []
|
|
59
59
|
post_inits = []
|
|
60
|
+
post_patches: list[str] = []
|
|
61
|
+
rewrites: list[tuple[str, str]] = []
|
|
60
62
|
ctx = {}
|
|
61
63
|
|
|
62
64
|
def walk(
|
|
63
65
|
*,
|
|
64
|
-
schema: StructType,
|
|
65
|
-
meta: Meta,
|
|
66
|
-
absolute_xpath: tuple[str, ...],
|
|
67
|
-
name: str = 'self',
|
|
68
|
-
parent_xname=None,
|
|
69
|
-
current_unique_type_name='cls',
|
|
70
|
-
offset=0
|
|
66
|
+
schema: StructType, # 当前处理的结构体的规格对象
|
|
67
|
+
meta: Meta, # 附加其上的元数据
|
|
68
|
+
absolute_xpath: tuple[str, ...], # 未经过修饰的字段路径(至当前字段)
|
|
69
|
+
name: str = 'self', # 当前处理的结构体对象被分配的临时变量名称
|
|
70
|
+
parent_xname=None, # 其父结构体对象被分配的临时变量名称
|
|
71
|
+
current_unique_type_name='cls', # 结构体的类型名
|
|
72
|
+
offset=0 # 字段绝对偏移量(从根结构体开始)
|
|
71
73
|
):
|
|
72
74
|
|
|
73
75
|
base = 'object' if meta.unsafe_create else current_unique_type_name
|
|
74
76
|
|
|
75
|
-
|
|
77
|
+
new_object_call = f'{base}.__new__({current_unique_type_name})'
|
|
76
78
|
|
|
77
|
-
# ctx[
|
|
79
|
+
# ctx[new_object_call] = lambda tobj=current_type_obj: tobj.__new__(tobj)
|
|
78
80
|
|
|
79
81
|
if len(absolute_xpath) > 1: # 在处理内嵌的结构体
|
|
82
|
+
# 需要分配临时变量储存新对象,减少 getattr 和 setattr 开销
|
|
80
83
|
current_field_name = absolute_xpath[-1]
|
|
81
84
|
|
|
82
85
|
update_add_code(f"{name} = {parent_xname}.{current_field_name}")
|
|
83
86
|
unpack_add_code(
|
|
84
|
-
f"{parent_xname}.{current_field_name} = {name} = {
|
|
87
|
+
f"{parent_xname}.{current_field_name} = {name} = {new_object_call}"
|
|
88
|
+
) # 组合赋值
|
|
85
89
|
else:
|
|
86
|
-
unpack_add_code(f"{name} = {
|
|
90
|
+
unpack_add_code(f"{name} = {new_object_call}") # 不需要临时变量存储根对象
|
|
87
91
|
# update 在这里不需要创建新对象
|
|
88
92
|
|
|
89
|
-
post_inits.append((name, schema.type_obj))
|
|
93
|
+
post_inits.append((name, schema.type_obj)) # 对于每个结构体,都可能需要调用后处理钩子,这里只添加。
|
|
90
94
|
|
|
91
95
|
for field in schema.fields: # 遍历字段
|
|
92
96
|
field_xpath = f'{name}.{field.name}'
|
|
97
|
+
m = field.meta
|
|
93
98
|
|
|
94
99
|
match field.type:
|
|
95
100
|
case StructType() as s:
|
|
96
|
-
if s.type_obj not in inner_classes:
|
|
97
|
-
typename =
|
|
101
|
+
if s.type_obj not in inner_classes: # 如果这个类型不在类型映射中,那么添加到里面,同时分配类名变量
|
|
102
|
+
typename = type_vars.new()
|
|
98
103
|
inner_classes[s.type_obj] = typename
|
|
99
104
|
else:
|
|
100
105
|
typename = inner_classes[s.type_obj]
|
|
@@ -116,10 +121,10 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
116
121
|
dtype = a.dtype
|
|
117
122
|
nbytes = a.size
|
|
118
123
|
|
|
119
|
-
array_name =
|
|
124
|
+
array_name = tmp_vars.new()
|
|
120
125
|
|
|
121
126
|
array_fields.append(
|
|
122
|
-
(array_name,
|
|
127
|
+
(array_name, tmp_vars.new(), field_xpath, dtype)
|
|
123
128
|
)
|
|
124
129
|
|
|
125
130
|
assigns.append(array_name)
|
|
@@ -127,15 +132,33 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
127
132
|
offset += nbytes
|
|
128
133
|
|
|
129
134
|
case BasicType() as b:
|
|
130
|
-
assigns.append(field_xpath)
|
|
131
135
|
offset += b.size
|
|
132
136
|
|
|
137
|
+
if m.trunc_nul:
|
|
138
|
+
assigns.append(var := tmp_vars.new())
|
|
139
|
+
|
|
140
|
+
if not m.encoding:
|
|
141
|
+
post_patches.append(fr'{var} = {var}.rstrip(b"\x00")')
|
|
142
|
+
else:
|
|
143
|
+
post_patches.append(fr'{var} = {var}.rstrip(b"\x00").decode({m.encoding!r})')
|
|
144
|
+
|
|
145
|
+
rewrites.append((var, field_xpath))
|
|
146
|
+
|
|
147
|
+
elif m.encoding:
|
|
148
|
+
assigns.append(var := tmp_vars.new())
|
|
149
|
+
|
|
150
|
+
post_patches.append(fr'{var} = {var}.decode({m.encoding!r})')
|
|
151
|
+
rewrites.append((var, field_xpath))
|
|
152
|
+
|
|
153
|
+
else:
|
|
154
|
+
assigns.append(field_xpath)
|
|
155
|
+
|
|
133
156
|
case x:
|
|
134
157
|
raise TypeError(f"Unexpected schema {x}")
|
|
135
158
|
|
|
136
159
|
walk(
|
|
137
160
|
schema=schema, meta=meta,
|
|
138
|
-
absolute_xpath=('self',
|
|
161
|
+
absolute_xpath=('self',),
|
|
139
162
|
)
|
|
140
163
|
|
|
141
164
|
assigns_expr = ', '.join(assigns)
|
|
@@ -148,7 +171,7 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
148
171
|
iter_unpack_inner.add_code(assign_code)
|
|
149
172
|
iter_update_inner.add_code(assign_code)
|
|
150
173
|
|
|
151
|
-
assign_code = f"{assigns_expr} = _unpack_from(buffer, offset)" # 生成
|
|
174
|
+
assign_code = f"{assigns_expr} = _unpack_from(buffer, offset)" # 生成 unpack_from 的赋值语句
|
|
152
175
|
unpack_from.add_code(assign_code)
|
|
153
176
|
update_from.add_code(assign_code)
|
|
154
177
|
|
|
@@ -204,6 +227,18 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
204
227
|
)
|
|
205
228
|
node.target = ast.Name('values', ast.Store())
|
|
206
229
|
|
|
230
|
+
for i in post_patches:
|
|
231
|
+
batch_add_code(
|
|
232
|
+
[unpack, unpack_from, iter_unpack_inner, iter_update_inner, update, update_from],
|
|
233
|
+
i
|
|
234
|
+
)
|
|
235
|
+
|
|
236
|
+
for src, dst in rewrites:
|
|
237
|
+
batch_add_code(
|
|
238
|
+
[unpack, unpack_from, iter_unpack_inner, iter_update_inner, update, update_from],
|
|
239
|
+
f'{dst} = {src}'
|
|
240
|
+
)
|
|
241
|
+
|
|
207
242
|
for field_xpath, type_obj in reversed(post_inits):
|
|
208
243
|
if hasattr(type_obj, '__post_unpack__'):
|
|
209
244
|
batch_add_code(
|
|
@@ -224,15 +259,15 @@ def create_unpack_methods(schema: StructType, meta: Meta = Meta()):
|
|
|
224
259
|
iter_unpack_inner.add_code('yield self')
|
|
225
260
|
iter_update_inner.add_code('yield self')
|
|
226
261
|
|
|
227
|
-
for _, array_obj_var, *_ in array_fields:
|
|
262
|
+
for _, array_obj_var, *_ in array_fields: # 对于 iter update,每次返回完需要清理已有的数据,才能进行下一次的填充
|
|
228
263
|
iter_update_inner.add_code(f'{array_obj_var}.clear()')
|
|
229
264
|
|
|
230
|
-
print("Unpack\n", unpack.generate_code(), sep='', end='\n\n')
|
|
231
|
-
print("Update\n", update.generate_code(), sep='', end='\n\n')
|
|
232
|
-
print("Unpack_from\n", unpack_from.generate_code(), sep='', end='\n\n')
|
|
233
|
-
print("Update_from\n", update_from.generate_code(), sep='', end='\n\n')
|
|
234
|
-
print("Iter_unpack\n", iter_unpack.generate_code(), sep='', end='\n\n')
|
|
235
|
-
print("Iter_update\n", iter_update.generate_code(), sep='', end='\n\n')
|
|
265
|
+
# print("Unpack\n", unpack.generate_code(), sep='', end='\n\n')
|
|
266
|
+
# print("Update\n", update.generate_code(), sep='', end='\n\n')
|
|
267
|
+
# print("Unpack_from\n", unpack_from.generate_code(), sep='', end='\n\n')
|
|
268
|
+
# print("Update_from\n", update_from.generate_code(), sep='', end='\n\n')
|
|
269
|
+
# print("Iter_unpack\n", iter_unpack.generate_code(), sep='', end='\n\n')
|
|
270
|
+
# print("Iter_update\n", iter_update.generate_code(), sep='', end='\n\n')
|
|
236
271
|
|
|
237
272
|
generated_struct = struct.Struct(schema.full_format_string)
|
|
238
273
|
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import array
|
|
2
|
+
import builtins
|
|
2
3
|
import sys
|
|
3
4
|
from typing import get_origin, Annotated, get_args
|
|
4
5
|
|
|
@@ -34,6 +35,7 @@ def parse_annotation(anno, disallow_custom_type=False) -> tuple[ArrayType | Basi
|
|
|
34
35
|
|
|
35
36
|
if hasattr(dtype, '__obstruct_schema__'):
|
|
36
37
|
dt = dtype.__obstruct_schema__
|
|
38
|
+
assert isinstance(dt, BasicType)
|
|
37
39
|
|
|
38
40
|
elif dtype in builtins_type_mapping:
|
|
39
41
|
dt = builtins_type_mapping[dtype]
|
|
@@ -48,6 +50,14 @@ def parse_annotation(anno, disallow_custom_type=False) -> tuple[ArrayType | Basi
|
|
|
48
50
|
meta.len
|
|
49
51
|
), meta
|
|
50
52
|
|
|
53
|
+
case builtins.str:
|
|
54
|
+
meta.encoding = 'utf-8'
|
|
55
|
+
return BasicType(f'{meta.len}s'), meta
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
case builtins.bytes:
|
|
59
|
+
return BasicType(f'{meta.len}s'), meta
|
|
60
|
+
|
|
51
61
|
case t if hasattr(t, '__obstruct_schema__'):
|
|
52
62
|
schema = t.__obstruct_schema__
|
|
53
63
|
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
def test_timeit(name, code, extra=''):
|
|
2
|
+
import timeit
|
|
3
|
+
import time
|
|
4
|
+
import dis
|
|
5
|
+
|
|
6
|
+
print()
|
|
7
|
+
print("Test: ", name)
|
|
8
|
+
|
|
9
|
+
code_obj = compile(code, '<string>', 'exec')
|
|
10
|
+
|
|
11
|
+
print("ByteCode for this Test")
|
|
12
|
+
dis.dis(code_obj)
|
|
13
|
+
|
|
14
|
+
res = timeit.repeat(
|
|
15
|
+
code,
|
|
16
|
+
number=NUMBER,
|
|
17
|
+
repeat=REPEAT,
|
|
18
|
+
timer=time.perf_counter_ns,
|
|
19
|
+
globals=globals(),
|
|
20
|
+
|
|
21
|
+
)
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
original_samples_len = len(res)
|
|
25
|
+
|
|
26
|
+
for i in range(TRIM_COUNT):
|
|
27
|
+
res.remove(max(res))
|
|
28
|
+
res.remove(min(res))
|
|
29
|
+
|
|
30
|
+
print("Original samples: ", original_samples_len)
|
|
31
|
+
print("Final samples:", len(res))
|
|
32
|
+
|
|
33
|
+
print(f'{NUMBER} steps finished in {sum(res) / (len(res)):.3f} ns in average. ({sum(res) / (len(res)) / NUMBER:.3f} ns per step)')
|
|
34
|
+
|
|
35
|
+
exec(extra, globals=globals()) if extra else None
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
NUMBER = 100000
|
|
40
|
+
TRIM_COUNT = 10
|
|
41
|
+
REPEAT = 100
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
new = object.__new__
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
class MyObject: ...
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
test_timeit('Call Directly', 'new(MyObject)')
|
|
51
|
+
test_timeit('Call from This Type', 'MyObject.__new__(MyObject)')
|
|
52
|
+
test_timeit('Call from object base', 'object.__new__(MyObject)')
|
|
53
|
+
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import time
|
|
2
|
+
from array import array
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
def test_timeit(name, code, extra=''):
|
|
6
|
+
import timeit
|
|
7
|
+
|
|
8
|
+
res = timeit.repeat(
|
|
9
|
+
code,
|
|
10
|
+
number=NUMBER,
|
|
11
|
+
repeat=REPEAT,
|
|
12
|
+
timer=time.perf_counter_ns,
|
|
13
|
+
globals=globals()
|
|
14
|
+
)
|
|
15
|
+
|
|
16
|
+
print()
|
|
17
|
+
|
|
18
|
+
original_samples_len = len(res)
|
|
19
|
+
|
|
20
|
+
for i in range(TRIM_COUNT):
|
|
21
|
+
res.remove(max(res))
|
|
22
|
+
res.remove(min(res))
|
|
23
|
+
|
|
24
|
+
print("Test: ", name)
|
|
25
|
+
print("Original samples: ", original_samples_len)
|
|
26
|
+
print("Final samples:", len(res))
|
|
27
|
+
|
|
28
|
+
print(f'{NUMBER} steps finished in {sum(res) / (len(res)):.3f} ns in average. ({sum(res) / (len(res)) / NUMBER:.3f} ns per step)')
|
|
29
|
+
|
|
30
|
+
exec(extra, globals=globals()) if extra else None
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
# print("\n\nMyStruct:", MyStruct.__cstruct__.size)
|
|
34
|
+
|
|
35
|
+
NUMBER = 1000
|
|
36
|
+
REPEAT = 256
|
|
37
|
+
TRIM_COUNT = 32
|
|
38
|
+
|
|
39
|
+
import struct
|
|
40
|
+
|
|
41
|
+
s1 = struct.Struct('i400si')
|
|
42
|
+
s2 = struct.Struct('i400xi')
|
|
43
|
+
|
|
44
|
+
data1 = memoryview(b'\x01' * s1.size)
|
|
45
|
+
data2 = memoryview(b'\x02' * s2.size)
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
test_timeit('string', "_, a, _ = s1.unpack(data1); array('i').frombytes(a)")
|
|
49
|
+
test_timeit('pad', "s2.unpack(data2); array('i').frombytes(data2[4:-4])")
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import dataclasses
|
|
2
|
+
from typing import Annotated
|
|
3
|
+
|
|
4
|
+
from obstruct import Struct, Meta
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
@dataclasses.dataclass()
|
|
8
|
+
class SomeStruct(Struct):
|
|
9
|
+
a: Annotated[bytes, Meta(len=10, trunc_nul=True)]
|
|
10
|
+
b: Annotated[str, Meta(len=10, trunc_nul=True)]
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
SomeStruct.__compile_struct__()
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
data = b'12345'.ljust(10, b'\x00') + '你好'.encode().ljust(10, b'\x00')
|
|
18
|
+
print(len(data), data)
|
|
19
|
+
|
|
20
|
+
print(SomeStruct.unpack_from(data))
|
|
21
|
+
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
"D:\Program Files\uv\uv.exe" run E:/.projects/obstruct/.venv/Scripts/python.exe E:\.projects\obstruct\test\test_speed.py
|
|
2
|
+
@classmethod
|
|
3
|
+
def unpack(cls, buffer):
|
|
4
|
+
self = __new__(cls)
|
|
5
|
+
self.a, self.b, self.c, self.d, self.e, self.f, self.g, self.h, self.i, self.j, self.k, self.l = _unpack(buffer)
|
|
6
|
+
return self
|
|
7
|
+
@classmethod
|
|
8
|
+
def unpack(cls, buffer):
|
|
9
|
+
buffer = memoryview(buffer)
|
|
10
|
+
self = __new__(cls)
|
|
11
|
+
self.x = B = __new__(A)
|
|
12
|
+
self.z = D = __new__(A)
|
|
13
|
+
B.a, B.b, B.c, B.d, B.e, B.f, B.g, B.h, B.i, B.j, B.k, B.l, D.a, D.b, D.c, D.d, D.e, D.f, D.g, D.h, D.i, D.j, D.k, D.l = _unpack(buffer)
|
|
14
|
+
self.y = _ = array('i')
|
|
15
|
+
_.frombytes(buffer[42:442])
|
|
16
|
+
B.__post_unpack__()
|
|
17
|
+
D.__post_unpack__()
|
|
18
|
+
return self
|
|
19
|
+
MyStruct size 42
|
|
20
|
+
AnotherStruct size 484
|
|
21
|
+
AnotherStruct: 484
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
Test: Pack
|
|
26
|
+
Results Length: 64
|
|
27
|
+
1000 steps finished in 241676.562 ns
|
|
28
|
+
Average: 241.677 ns per step
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
Post Hook Called: False
|
|
32
|
+
|
|
33
|
+
Test: Unpack
|
|
34
|
+
Results Length: 64
|
|
35
|
+
1000 steps finished in 574932.812 ns
|
|
36
|
+
Average: 574.933 ns per step
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
Post Hook Called: False
|
|
40
|
+
|
|
41
|
+
Test: Complex Pack
|
|
42
|
+
Results Length: 64
|
|
43
|
+
1000 steps finished in 1274254.688 ns
|
|
44
|
+
Average: 1274.255 ns per step
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
Post Hook Called: False
|
|
48
|
+
|
|
49
|
+
Test: Complex Unpack
|
|
50
|
+
Results Length: 64
|
|
51
|
+
1000 steps finished in 1800114.062 ns
|
|
52
|
+
Average: 1800.114 ns per step
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
Post Hook Called: True
|
|
56
|
+
|
|
57
|
+
Test: Update
|
|
58
|
+
Results Length: 64
|
|
59
|
+
1000 steps finished in 346839.062 ns
|
|
60
|
+
Average: 346.839 ns per step
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
Post Hook Called: False
|
|
64
|
+
|
|
65
|
+
Test: Iter Unpack (100x)
|
|
66
|
+
Results Length: 64
|
|
67
|
+
1000 steps finished in 40875885.938 ns
|
|
68
|
+
Average: 40875.886 ns per step
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
Post Hook Called: False
|
|
72
|
+
|
|
73
|
+
Test: Iter Update (100x)
|
|
74
|
+
Results Length: 64
|
|
75
|
+
1000 steps finished in 30352537.500 ns
|
|
76
|
+
Average: 30352.537 ns per step
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
Post Hook Called: False
|
|
80
|
+
|
|
81
|
+
Test: Unpack From
|
|
82
|
+
Results Length: 64
|
|
83
|
+
1000 steps finished in 480523.438 ns
|
|
84
|
+
Average: 480.523 ns per step
|
|
85
|
+
|
|
86
|
+
|
|
87
|
+
Post Hook Called: False
|
|
88
|
+
|
|
89
|
+
Test: Update From
|
|
90
|
+
Results Length: 64
|
|
91
|
+
1000 steps finished in 285021.875 ns
|
|
92
|
+
Average: 285.022 ns per step
|
|
93
|
+
|
|
94
|
+
|
|
95
|
+
Post Hook Called: False
|
|
96
|
+
|
|
97
|
+
Test: Complex Update
|
|
98
|
+
Results Length: 64
|
|
99
|
+
1000 steps finished in 813121.875 ns
|
|
100
|
+
Average: 813.122 ns per step
|
|
101
|
+
|
|
102
|
+
|
|
103
|
+
Post Hook Called: True
|
|
104
|
+
|
|
105
|
+
Test: Complex Iter Unpack (100x)
|
|
106
|
+
Results Length: 64
|
|
107
|
+
1000 steps finished in 131775840.625 ns
|
|
108
|
+
Average: 131775.841 ns per step
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
Post Hook Called: True
|
|
112
|
+
|
|
113
|
+
Test: Complex Iter Update (100x)
|
|
114
|
+
Results Length: 64
|
|
115
|
+
1000 steps finished in 88616110.938 ns
|
|
116
|
+
Average: 88616.111 ns per step
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
Post Hook Called: True
|
|
120
|
+
|
|
121
|
+
Test: Complex Unpack From (100x)
|
|
122
|
+
Results Length: 64
|
|
123
|
+
1000 steps finished in 1467882.812 ns
|
|
124
|
+
Average: 1467.883 ns per step
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
Post Hook Called: True
|
|
128
|
+
|
|
129
|
+
Test: Complex Update From (100x)
|
|
130
|
+
Results Length: 64
|
|
131
|
+
1000 steps finished in 909548.438 ns
|
|
132
|
+
Average: 909.548 ns per step
|
|
133
|
+
|
|
134
|
+
|
|
135
|
+
Post Hook Called: True
|
|
136
|
+
|
|
137
|
+
进程已结束,退出代码为 0
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
version = "0.6.0"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|