Skip to content

Commit 8f97702

Browse files
authored
deep copy for deref tuple, list, dict (#184)
* do a copy for dictionary lookup * Deep copy for list de-ref * Tuple deref also now triggers a copy
1 parent 6f98f02 commit 8f97702

File tree

2 files changed

+46
-5
lines changed

2 files changed

+46
-5
lines changed

func_adl/ast/function_simplifier.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -453,7 +453,7 @@ def visit_Subscript_Tuple(self, v: ast.Tuple, s: ast.Constant):
453453
f" {len(v.elts)} values long."
454454
)
455455

456-
return v.elts[n]
456+
return copy.deepcopy(v.elts[n])
457457

458458
def visit_Subscript_List(self, v: ast.List, s: ast.Constant):
459459
"""
@@ -470,7 +470,7 @@ def visit_Subscript_List(self, v: ast.List, s: ast.Constant):
470470
f" only {len(v.elts)} values long."
471471
)
472472

473-
return v.elts[n]
473+
return copy.deepcopy(v.elts[n])
474474

475475
def visit_Subscript_Dict(self, v: ast.Dict, s: ast.Constant):
476476
"""
@@ -485,7 +485,7 @@ def visit_Subscript_Dict_with_value(self, v: ast.Dict, s: Union[str, int]):
485485
for index, value in enumerate(v.keys):
486486
assert isinstance(value, ast.Constant)
487487
if value.value == s:
488-
return v.values[index]
488+
return copy.deepcopy(v.values[index])
489489

490490
return ast.Subscript(v, s, ast.Load()) # type: ignore
491491

tests/ast/test_function_simplifier.py

Lines changed: 43 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
import ast
2+
import copy
3+
from typing import cast
24

35
from astunparse import unparse
6+
47
from func_adl.ast.function_simplifier import FuncADLIndexError, simplify_chained_calls
58
from tests.util_debug_ast import normalize_ast
69

@@ -18,10 +21,14 @@ def util_process(ast_in, ast_out):
1821
a_updated_raw = simplify_chained_calls().visit(a_source)
1922

2023
s_updated = ast.dump(
21-
normalize_ast().visit(a_updated_raw), annotate_fields=False, include_attributes=False
24+
normalize_ast().visit(copy.deepcopy(a_updated_raw)),
25+
annotate_fields=False,
26+
include_attributes=False,
2227
)
2328
s_expected = ast.dump(
24-
normalize_ast().visit(a_expected), annotate_fields=False, include_attributes=False
29+
normalize_ast().visit(copy.deepcopy(a_expected)),
30+
annotate_fields=False,
31+
include_attributes=False,
2532
)
2633

2734
print(s_updated)
@@ -183,11 +190,27 @@ def test_tuple_select():
183190
util_process("(t1,t2)[0]", "t1")
184191

185192

193+
def test_tuple_select_copy_made():
194+
# (t1, t2)[0] should be t1.
195+
root = ast.parse("(t1,t2)[0]")
196+
orig = root.body[0].value.value.elts[0] # type: ignore
197+
r1 = util_process(root, "t1")
198+
assert r1.body[0].value != orig
199+
200+
186201
def test_list_select():
187202
# [t1, t2][0] should be t1.
188203
util_process("[t1,t2][0]", "t1")
189204

190205

206+
def test_list_select_copy_made():
207+
# [t1, t2][0] should be t1.
208+
root = ast.parse("[t1,t2][0]")
209+
orig = root.body[0].value.value.elts[0] # type: ignore
210+
r1 = util_process(root, "t1")
211+
assert r1.body[0].value != orig
212+
213+
191214
def test_tuple_select_past_end():
192215
# This should cause a crash!
193216
try:
@@ -260,3 +283,21 @@ def test_dict_around_first():
260283
'Select(events, lambda e: First(Select(e.jets, lambda j: {"j": j, "e": e})).j)',
261284
"Select(events, lambda e: First(e.jets))",
262285
)
286+
287+
288+
def test_dict_is_different_attrib():
289+
"Make sure we are returning different ast's that have the same content"
290+
root = cast(ast.expr, ast.parse('{"n1": t1, "n2": t2}.n1'))
291+
orig_name = root.body[0].value.value.values[0] # type: ignore
292+
r1 = util_process(root, "t1")
293+
294+
assert r1.body[0].value != orig_name
295+
296+
297+
def test_dict_is_different():
298+
"Make sure we are returning different ast's that have the same content"
299+
root = cast(ast.expr, ast.parse('{"n1": t1, "n2": t2}["n1"]'))
300+
orig_name = root.body[0].value.value.values[0] # type: ignore
301+
r1 = util_process(root, "t1")
302+
303+
assert r1.body[0].value != orig_name

0 commit comments

Comments
 (0)