ripple-down-rules 0.5.52__py3-none-any.whl → 0.5.54__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.
- ripple_down_rules/__init__.py +1 -1
- ripple_down_rules/datastructures/callable_expression.py +14 -8
- ripple_down_rules/experts.py +4 -1
- {ripple_down_rules-0.5.52.dist-info → ripple_down_rules-0.5.54.dist-info}/METADATA +1 -1
- {ripple_down_rules-0.5.52.dist-info → ripple_down_rules-0.5.54.dist-info}/RECORD +8 -8
- {ripple_down_rules-0.5.52.dist-info → ripple_down_rules-0.5.54.dist-info}/WHEEL +0 -0
- {ripple_down_rules-0.5.52.dist-info → ripple_down_rules-0.5.54.dist-info}/licenses/LICENSE +0 -0
- {ripple_down_rules-0.5.52.dist-info → ripple_down_rules-0.5.54.dist-info}/top_level.txt +0 -0
ripple_down_rules/__init__.py
CHANGED
@@ -93,7 +93,6 @@ class CallableExpression(SubclassJSONSerializer):
|
|
93
93
|
A callable that is constructed from a string statement written by an expert.
|
94
94
|
"""
|
95
95
|
encapsulating_function_name: str = "_get_value"
|
96
|
-
encapsulating_function: str = f"def {encapsulating_function_name}(case):"
|
97
96
|
|
98
97
|
def __init__(self, user_input: Optional[str] = None,
|
99
98
|
conclusion_type: Optional[Tuple[Type]] = None,
|
@@ -117,7 +116,7 @@ class CallableExpression(SubclassJSONSerializer):
|
|
117
116
|
if user_input is None:
|
118
117
|
user_input = build_user_input_from_conclusion(conclusion)
|
119
118
|
self.conclusion: Optional[Any] = conclusion
|
120
|
-
self._user_input: str = encapsulate_user_input(user_input, self.
|
119
|
+
self._user_input: str = encapsulate_user_input(user_input, self.get_encapsulating_function())
|
121
120
|
if conclusion_type is not None:
|
122
121
|
if is_iterable(conclusion_type):
|
123
122
|
conclusion_type = tuple(conclusion_type)
|
@@ -132,6 +131,13 @@ class CallableExpression(SubclassJSONSerializer):
|
|
132
131
|
self.visitor.visit(self.expression_tree)
|
133
132
|
self.mutually_exclusive: bool = mutually_exclusive
|
134
133
|
|
134
|
+
@classmethod
|
135
|
+
def get_encapsulating_function(cls, postfix: str = '') -> str:
|
136
|
+
"""
|
137
|
+
Get the encapsulating function that is used to wrap the user input.
|
138
|
+
"""
|
139
|
+
return f"def {cls.encapsulating_function_name}{postfix}(case):"
|
140
|
+
|
135
141
|
def __call__(self, case: Any, **kwargs) -> Any:
|
136
142
|
try:
|
137
143
|
if self.user_input is not None:
|
@@ -161,8 +167,8 @@ class CallableExpression(SubclassJSONSerializer):
|
|
161
167
|
"""
|
162
168
|
Combine this callable expression with another callable expression using the 'and' operator.
|
163
169
|
"""
|
164
|
-
cond1_user_input = self.user_input.replace(self.
|
165
|
-
cond2_user_input = other.user_input.replace(self.
|
170
|
+
cond1_user_input = self.user_input.replace(self.get_encapsulating_function(), "def _cond1(case):")
|
171
|
+
cond2_user_input = other.user_input.replace(self.get_encapsulating_function(), "def _cond2(case):")
|
166
172
|
new_user_input = (f"{cond1_user_input}\n"
|
167
173
|
f"{cond2_user_input}\n"
|
168
174
|
f"return _cond1(case) and _cond2(case)")
|
@@ -175,7 +181,7 @@ class CallableExpression(SubclassJSONSerializer):
|
|
175
181
|
new_function_body = extract_function_source(file_path, [function_name])[function_name]
|
176
182
|
if new_function_body is None:
|
177
183
|
return
|
178
|
-
self.user_input = self.
|
184
|
+
self.user_input = self.get_encapsulating_function() + '\n' + new_function_body
|
179
185
|
|
180
186
|
def write_to_python_file(self, file_path: str, append: bool = False):
|
181
187
|
"""
|
@@ -208,7 +214,7 @@ class CallableExpression(SubclassJSONSerializer):
|
|
208
214
|
Set the user input.
|
209
215
|
"""
|
210
216
|
if value is not None:
|
211
|
-
self._user_input = encapsulate_user_input(value, self.
|
217
|
+
self._user_input = encapsulate_user_input(value, self.get_encapsulating_function())
|
212
218
|
self.scope = get_used_scope(self.user_input, self.scope)
|
213
219
|
self.expression_tree = parse_string_to_expression(self.user_input)
|
214
220
|
self.code = compile_expression_to_code(self.expression_tree)
|
@@ -286,8 +292,8 @@ def parse_string_to_expression(expression_str: str) -> AST:
|
|
286
292
|
:param expression_str: The string which will be parsed.
|
287
293
|
:return: The parsed expression.
|
288
294
|
"""
|
289
|
-
if not expression_str.startswith(CallableExpression.
|
290
|
-
expression_str = encapsulate_user_input(expression_str, CallableExpression.
|
295
|
+
if not expression_str.startswith(CallableExpression.get_encapsulating_function()):
|
296
|
+
expression_str = encapsulate_user_input(expression_str, CallableExpression.get_encapsulating_function())
|
291
297
|
mode = 'exec' if expression_str.startswith('def') else 'eval'
|
292
298
|
tree = ast.parse(expression_str, mode=mode)
|
293
299
|
logging.debug(f"AST parsed successfully: {ast.dump(tree)}")
|
ripple_down_rules/experts.py
CHANGED
@@ -147,7 +147,7 @@ class Expert(ABC):
|
|
147
147
|
imports = ''
|
148
148
|
if func_source is not None:
|
149
149
|
uid = uuid.uuid4().hex
|
150
|
-
func_source = encapsulate_user_input(func_source, CallableExpression.
|
150
|
+
func_source = encapsulate_user_input(func_source, CallableExpression.get_encapsulating_function(f'_{uid}'))
|
151
151
|
else:
|
152
152
|
func_source = 'pass # No user input provided for this case.\n'
|
153
153
|
f.write(imports + func_source + '\n' + '\n\n\n\'===New Answer===\'\n\n\n')
|
@@ -194,6 +194,7 @@ class Expert(ABC):
|
|
194
194
|
answer = answer.strip('\n').strip()
|
195
195
|
if 'def ' not in answer and 'pass' in answer:
|
196
196
|
self.all_expert_answers.append(({}, None))
|
197
|
+
continue
|
197
198
|
scope = extract_imports(tree=ast.parse(answer))
|
198
199
|
function_source = all_function_sources[i].replace(all_function_sources_names[i],
|
199
200
|
CallableExpression.encapsulating_function_name)
|
@@ -240,6 +241,7 @@ class Human(Expert):
|
|
240
241
|
except IndexError:
|
241
242
|
self.use_loaded_answers = False
|
242
243
|
if user_input is not None:
|
244
|
+
case_query.scope.update(loaded_scope)
|
243
245
|
condition = CallableExpression(user_input, bool, scope=case_query.scope)
|
244
246
|
else:
|
245
247
|
user_input, condition = self.user_prompt.prompt_user_for_expression(case_query, PromptFor.Conditions)
|
@@ -265,6 +267,7 @@ class Human(Expert):
|
|
265
267
|
try:
|
266
268
|
loaded_scope, expert_input = self.all_expert_answers.pop(0)
|
267
269
|
if expert_input is not None:
|
270
|
+
case_query.scope.update(loaded_scope)
|
268
271
|
expression = CallableExpression(expert_input, case_query.attribute_type,
|
269
272
|
scope=case_query.scope,
|
270
273
|
mutually_exclusive=case_query.mutually_exclusive)
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: ripple_down_rules
|
3
|
-
Version: 0.5.
|
3
|
+
Version: 0.5.54
|
4
4
|
Summary: Implements the various versions of Ripple Down Rules (RDR) for knowledge representation and reasoning.
|
5
5
|
Author-email: Abdelrhman Bassiouny <abassiou@uni-bremen.de>
|
6
6
|
License: GNU GENERAL PUBLIC LICENSE
|
@@ -1,5 +1,5 @@
|
|
1
|
-
ripple_down_rules/__init__.py,sha256=
|
2
|
-
ripple_down_rules/experts.py,sha256=
|
1
|
+
ripple_down_rules/__init__.py,sha256=mzIshJxvvzvb07mJJq9BA3f-iThLZ1syaNYjbttiz8g,100
|
2
|
+
ripple_down_rules/experts.py,sha256=8p5tFOWuQWgp9gt-6Yr6MFFphOTmpI9IJ3iepUyy3FY,12266
|
3
3
|
ripple_down_rules/helpers.py,sha256=TvTJU0BA3dPcAyzvZFvAu7jZqsp8Lu0HAAwvuizlGjg,2018
|
4
4
|
ripple_down_rules/rdr.py,sha256=FJYuRXgpUYSSK1pYrp2yeXb_ZZ2xjPED31tzxofokL4,48865
|
5
5
|
ripple_down_rules/rdr_decorators.py,sha256=pYCKLgMKgQ6x_252WQtF2t4ZNjWPBxnaWtJ6TpGdcc0,7820
|
@@ -7,7 +7,7 @@ ripple_down_rules/rules.py,sha256=TPNVMqW9T-_46BS4WemrspLg5uG8kP6tsPvWWBAzJxg,17
|
|
7
7
|
ripple_down_rules/start-code-server.sh,sha256=otClk7VmDgBOX2TS_cjws6K0UwvgAUJhoA0ugkPCLqQ,949
|
8
8
|
ripple_down_rules/utils.py,sha256=4xQ5gmIeMsY-mA9g-4cedKt2WJq4oZAMs5XEKeplWPM,51127
|
9
9
|
ripple_down_rules/datastructures/__init__.py,sha256=V2aNgf5C96Y5-IGghra3n9uiefpoIm_QdT7cc_C8cxQ,111
|
10
|
-
ripple_down_rules/datastructures/callable_expression.py,sha256=
|
10
|
+
ripple_down_rules/datastructures/callable_expression.py,sha256=w6Gpo1o-xnFvTaPrzJ2w7VgCjSr1xqp8LQG0jAl-mfc,12718
|
11
11
|
ripple_down_rules/datastructures/case.py,sha256=r8kjL9xP_wk84ThXusspgPMrAoed2bGQmKi54fzhmH8,15258
|
12
12
|
ripple_down_rules/datastructures/dataclasses.py,sha256=PuD-7zWqWT2p4FnGvnihHvZlZKg9A1ctnFgVYf2cs-8,8554
|
13
13
|
ripple_down_rules/datastructures/enums.py,sha256=ce7tqS0otfSTNAOwsnXlhsvIn4iW_Y_N3TNebF3YoZs,5700
|
@@ -17,8 +17,8 @@ ripple_down_rules/user_interface/ipython_custom_shell.py,sha256=24MIFwqnAhC6ofOb
|
|
17
17
|
ripple_down_rules/user_interface/object_diagram.py,sha256=tsB6iuLNEbHxp5lR2WjyejjWbnAX_nHF9xS8jNPOQVk,4548
|
18
18
|
ripple_down_rules/user_interface/prompt.py,sha256=AkkltdDIaioN43lkRKDPKSjJcmdSSGZDMYz7AL7X9lE,8082
|
19
19
|
ripple_down_rules/user_interface/template_file_creator.py,sha256=FGtLfYBfr4310c7Dfa9b2qiOWLNzHk1q3kdhD70Ilg4,13804
|
20
|
-
ripple_down_rules-0.5.
|
21
|
-
ripple_down_rules-0.5.
|
22
|
-
ripple_down_rules-0.5.
|
23
|
-
ripple_down_rules-0.5.
|
24
|
-
ripple_down_rules-0.5.
|
20
|
+
ripple_down_rules-0.5.54.dist-info/licenses/LICENSE,sha256=ixuiBLtpoK3iv89l7ylKkg9rs2GzF9ukPH7ynZYzK5s,35148
|
21
|
+
ripple_down_rules-0.5.54.dist-info/METADATA,sha256=Enz4rrNXQ3GZeyz4T0Pbai-ZS4tJu2y9OH_hVfKKIiQ,48189
|
22
|
+
ripple_down_rules-0.5.54.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
23
|
+
ripple_down_rules-0.5.54.dist-info/top_level.txt,sha256=VeoLhEhyK46M1OHwoPbCQLI1EifLjChqGzhQ6WEUqeM,18
|
24
|
+
ripple_down_rules-0.5.54.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|