You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
[Bug]: Modifying NumPy array after passing to set_xticks() unexpectedly alters plot ticks #32313
When passing a NumPy array to ax.set_xticks(), Matplotlib retains a reference to the array instead of creating a copy. Any in-place modifications made to the array after calling set_xticks() directly mutate the plot's tick locations. Passing a standard Python list does not exhibit this issue, suggesting Matplotlib should create an explicit copy of array input internally.
@williamlus are these actual production bugs you are stumbling over or are you running tools that inverstigate theoretical error paths.
On the array-modification topic: I'm unclear whether we have a general guarantee that we isolate from passed parameters. Sometimes we do explicitly, but this is really a can of worms. Effectively, one would have to push copying down to https://github.com/matplotlib/matplotlib/blob/v3.11.1/lib/matplotlib/axis.py#L2309. But there unit conversion may or may not produce a new array. While we could change that to always make a copy, the result is passed in FixedLocator. But FixedLocator can also be used as public API directly, so that it itself would need to do a copy to defend against post-hoc modification. This means we need to do multiple unnecessary copies.
Overall, I would say, that the behavior is explicitly not defined. You should not use modify ticks through this mechanism, but we also don't guarantee that objects are decoupled.
Sorry for bothering you with this! To be completely honest, I started out working in production, but later found software testing and bug hunting really fascinating, so I built a tool to help discover potential edge cases like this one.
I shared it because I found the behavior quite interesting—modifying the array after passing it to the first subplot implicitly alters the tick locations for both subplots. Here is the complete minimal code snippet to demonstrate the behavior. In this case you still need to manually make a copy of the theta array for the second plot (for example, theta = theta + np.pi * 2) before modifying it.
Hi, I’m interested in investigating this issue. I read the discussion here and the closed #32367, and my understanding is that simply copying inside FixedLocator is not sufficient because the broader question is whether Matplotlib should guarantee isolation from mutations of caller-provided arrays.
Before implementing anything, would you prefer this behavior to remain undefined, or is there an API boundary where you would consider copying the input appropriate? If a copy/isolation guarantee is desired, I’d be happy to trace the set_ticks/unit-conversion/FixedLocator paths and add tests for the agreed behavior.
Activity
timhoffm commentedon Sep 7, 2026
@williamlus are these actual production bugs you are stumbling over or are you running tools that inverstigate theoretical error paths.
On the array-modification topic: I'm unclear whether we have a general guarantee that we isolate from passed parameters. Sometimes we do explicitly, but this is really a can of worms. Effectively, one would have to push copying down to https://github.com/matplotlib/matplotlib/blob/v3.11.1/lib/matplotlib/axis.py#L2309. But there unit conversion may or may not produce a new array. While we could change that to always make a copy, the result is passed in
FixedLocator. But FixedLocator can also be used as public API directly, so that it itself would need to do a copy to defend against post-hoc modification. This means we need to do multiple unnecessary copies.Overall, I would say, that the behavior is explicitly not defined. You should not use modify ticks through this mechanism, but we also don't guarantee that objects are decoupled.
williamlus commentedon Sep 8, 2026
Sorry for bothering you with this! To be completely honest, I started out working in production, but later found software testing and bug hunting really fascinating, so I built a tool to help discover potential edge cases like this one.
I shared it because I found the behavior quite interesting—modifying the array after passing it to the first subplot implicitly alters the tick locations for both subplots. Here is the complete minimal code snippet to demonstrate the behavior. In this case you still need to manually make a copy of the theta array for the second plot (for example, theta = theta + np.pi * 2) before modifying it.
Rudra-G-23 commentedon Sep 19, 2026
Hi, I’m interested in investigating this issue. I read the discussion here and the closed #32367, and my understanding is that simply copying inside
FixedLocatoris not sufficient because the broader question is whether Matplotlib should guarantee isolation from mutations of caller-provided arrays.Before implementing anything, would you prefer this behavior to remain undefined, or is there an API boundary where you would consider copying the input appropriate? If a copy/isolation guarantee is desired, I’d be happy to trace the
set_ticks/unit-conversion/FixedLocatorpaths and add tests for the agreed behavior.