Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

eendebakpt
Copy link
Contributor

@eendebakpt eendebakpt commented Jul 3, 2023

PR summary

This PR improves performance of plt.clf(). By setting spines.axis to None a double call to XAxis.clear() and YAxis.clear() is avoided.

Benchmark script:

import time
import matplotlib
from matplotlib import axis
import matplotlib.pyplot as plt
print(matplotlib.__version__)

def go():
	t0=time.perf_counter()
	for ii in range(5):
		plt.figure(100)
		plt.clf()
		plt.plot(range(20), range(20,40), label='hi')
		plt.legend()
		
	dt=time.perf_counter()	-t0
	return dt
	
niter=10
x=[]
for ii in range(niter):
    dt=go()	
    print(f'round {ii}: {dt:2f} [s]')
    x.append(dt)
    
print(f'mean: {sum(x)/niter:.2f} [s]')    

Performance on main:

3.8.0.dev1461+gf017315dd5
round 0: 0.329322 [s]
round 1: 0.173158 [s]
round 2: 0.196067 [s]
round 3: 0.167451 [s]
round 4: 0.170085 [s]
round 5: 0.169859 [s]
round 6: 0.203656 [s]
round 7: 0.167369 [s]
round 8: 0.170247 [s]
round 9: 0.166873 [s]
mean: 0.19 [s]

Performance on PR

3.8.0.dev1463+gbff26576f7
round 0: 0.276565 [s]
round 1: 0.088187 [s]
round 2: 0.089832 [s]
round 3: 0.089987 [s]
round 4: 0.111984 [s]
round 5: 0.089566 [s]
round 6: 0.086931 [s]
round 7: 0.087903 [s]
round 8: 0.090093 [s]
round 9: 0.085896 [s]
mean: 0.11 [s]

Also see #23771

PR checklist

  • [N/A] "closes #0000" is in the body of the PR description to link the related issue. Issue is mentioned, but this PR does not fully address the issue.
  • new and changed code is tested
  • [N/A ] Plotting related features are demonstrated in an example
  • [N/A] New Features and API Changes are noted with a directive and release note
  • [N/A] Documentation complies with general and docstring guidelines

@tacaswell
Copy link
Member

Where does the axis on the spine get re-set to not None?

@eendebakpt
Copy link
Contributor Author

Where does the axis on the spine get re-set to not None?

Thanks for the quick review, resetting the spine is indeed necessary. Not sure whether this is enough (I am still setting up tests locally), but the performance improvement seems worthwhile.

@oscargus
Copy link
Member

oscargus commented Jul 4, 2023

I'd just like to point out #26164.

@eendebakpt eendebakpt changed the title Draft: improve performance of plt.clf() Improve performance of plt.clf() Jul 4, 2023
@eendebakpt
Copy link
Contributor Author

@tacaswell Tests are passing now. The PR assumes the axis in the spines objects are the same as in self._axis_map. If this is not always the case, we could also do something like:

        cleared_axis = list( self._axis_map.values() )
        for spine in self.spines.values():
            # avoid expensive methods in the clearing of the spine, gh-26243            
            tmp_axis = spine.axis
            if tmp_axis in cleared_axis:
                spine.axis = None
            else:
                 cleared_axis.append(tmp_axis)
            spine.clear()
            spine.axis = tmp_axis

for spine in self.spines.values():
# avoid expensive methods in the clearing of the spine, gh-26243
tmp_axis = spine.axis
spine.axis = None
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We have a context manager that will do this setting/resetting in matplotlib.cbook._setattr_cm.

@tacaswell
Copy link
Member

@eendebakpt I think that the way this is addressed in #26164 is a better way to address this as it avoids patching monkeying with spine state (at the cost of a new private method).

@eendebakpt
Copy link
Contributor Author

@eendebakpt I think that the way this is addressed in #26164 is a better way to address this as it avoids patching monkeying with spine state (at the cost of a new private method).

I tested #26164 with the benchmark script from this PR and the performance gain is comparable. If that PR is merged, I will close this one.

@eendebakpt
Copy link
Contributor Author

Closing in favor of #26164

@eendebakpt eendebakpt closed this Jul 8, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants