Ask Your Question
2

Potential bug on interacts using lists

asked 2020-04-04 20:37:46 +0100

dsejas gravatar image

updated 2020-04-04 20:45:13 +0100

Hello, Sage Community! While trying to solve this question, I have identified a potential bug. Consider the following code:

def test(xL=[]):
    xL.append(1)
    return xL

@interact
def _(x=slider(0,10,1,1)):
    f = test()
    show(f)

This is a MWE of the problem presented in the question I mentioned. For what I understand, this code should show an slide, and print [1], no matter where the slider is positioned. However, the actual behavior is that it indeed shows [1] the first time the code is executed, but then, every time I move the slider, the list grows appending one more 1.

Even though the default value for xL in the first subroutine (test()) is xL = [], and I am calling it with no arguments, it seems that the previous value of xL (corresponding to the previous position of the slider) is passed every time the slider is moved. In particular, if I execute this code and move the slider three times, I get the output

[1, 1, 1, 1]

On the other hand, if I specifically pass the empty list [] to test(), like in

f = test([])

then, the result is always [1].

Can somebody confirm and explain this? Is this a bug?

edit retag flag offensive close merge delete

1 Answer

Sort by » oldest newest most voted
2

answered 2020-04-04 23:38:06 +0100

Juanjo gravatar image

updated 2020-04-05 04:15:44 +0100

It is not really a SageMath problem, but a Python one. I do not know why xL is not the empty list each time that test() is called, according to the default value of xL in your definition of test. However, this happens even if such a default value is not an empty list, as you can check with any Python interpreter:

>>> def test(xL=[0]):
...     xL.append(len(xL))
...     return xL
... 
>>> for i in range(3):
...     print(test())
... 
[0, 1]
[0, 1, 2]
[0, 1, 2, 3]

However, if one uses concatenation instead of the append method, one gets the expected behaviour:

>>> def test(xL=[0]):
...     return xL + [len(xL)]
... 
>>> for i in range(3):
...     print(test())
... 
[0, 1]
[0, 1]
[0, 1]
edit flag offensive delete link more

Comments

2

One should not use mutable types as default arguments.

FrédéricC gravatar imageFrédéricC ( 2020-04-05 10:12:30 +0100 )edit
ortollj gravatar imageortollj ( 2020-04-05 12:36:56 +0100 )edit

Your Answer

Please start posting anonymously - your entry will be published after you log in or create a new account.

Add Answer

Question Tools

2 followers

Stats

Asked: 2020-04-04 20:37:46 +0100

Seen: 313 times

Last updated: Apr 05 '20