Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Imshow does not copy data array but determines colormap values upon call #6419

Closed
kgabor opened this issue May 13, 2016 · 5 comments
Closed
Assignees
Labels
Release critical For bugs that make the library unusable (segfaults, incorrect plots, etc) and major regressions.
Milestone

Comments

@kgabor
Copy link

kgabor commented May 13, 2016

The following code produces a horizontal gradient plot instead of a horizontal line:

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.cm

Z=np.zeros((100,100))
Z[50]=100
fig=plt.figure()
ax=fig.add_subplot(1,1,1)
ax.imshow(Z,cmap=matplotlib.cm.Greys)
Z[...]= np.arange(100.)[np.newaxis,:]

plt.show() 

Please note that if we comment Z[50]=100 the issue is not apparent as an all white figure is created as expected, but e.g. in Qt4Agg backend, mouseover values shows the altered Z values.

This means that imshow does not copy the data array but sets the color scale at the ax.imshow() call.

If data is intentionally not copied, I'd suggest adding a big warning about this behavior in the documentation and then the colorscale determination should be deferred until the figure is actually drawn. Otherwise the data should be copied.

  • pip installed Matplotlib: 1.5.0, numpy: 1.10.1
  • Ubuntu 14.04 python: 3.4.3
@tacaswell tacaswell added this to the 1.5.2 (Critical bug fix release) milestone May 13, 2016
@tacaswell tacaswell added the Release critical For bugs that make the library unusable (segfaults, incorrect plots, etc) and major regressions. label May 13, 2016
@tacaswell
Copy link
Member

Data should be copied.

@efiring
Copy link
Member

efiring commented May 13, 2016

_AxesImageBase.set_data simply passes the input array through cbook.safe_masked_invalid, which explicitly does not copy. I don't remember whether at some point, perhaps long ago, there was a decision to save time and memory by avoiding the copy, or whether this is just accidental. In any case, maybe the thing to do is add a 'copy' kwarg to safe_masked_invalid and then change its first line to use that flag in a call to array(..., subok=True, ...) in place of the present asanyarray.

I can make a PR for that today.

@tacaswell
Copy link
Member

If you throw a fig.canvas.draw() between calling imshow and changing Z it works correctly. We are deferring some operation a bit too long.

@efiring
Copy link
Member

efiring commented May 13, 2016

To prevent the problem illustrated here, it is essential to copy Z in imshow, as I proposed above. The only remaining question is whether this means we can remove a copy somewhere else, on the grounds that now we know we are safe. We tend to view the question of copying from the standpoint that we don't want mpl to modify an array that is referenced from outside mpl; but the issue here is from a different standpoint, that we don't want an array used inside mpl to be modified from outside.

@efiring
Copy link
Member

efiring commented May 15, 2016

Closed by #6422

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Release critical For bugs that make the library unusable (segfaults, incorrect plots, etc) and major regressions.
Projects
None yet
Development

No branches or pull requests

3 participants