In sympy plotting, how can I get a plot with a fixed aspect ratio?

我与影子孤独终老i 提交于 2019-12-10 13:19:59

问题


If I plot a circle with this snippet

from sympy import *
x, y = symbols('x y')        
p1 = plot_implicit(Eq(x**2 +y**2, 1),aspect_ratio=(1.,1.))

I will get a figure window like this one

Now the aspect ratio is not what I was expecting because I see an ellipse instead of a circle. Moreover, if I change the aspect ratio of the window (dragging the bottom-right corner of the window) I get also a change in the aspect ratio of the plot... The following image is what I get after dragging the corner in order to see a circle:

I would like to get a plot like the one you get in Matlab when you set axis equal, see http://it.mathworks.com/help/matlab/creating_plots/aspect-ratio-for-2-d-axes.html when you plot an ellipse

What am I missing?

I am using Jupyter and the version of the notebook server is 4.1.0 and is running on: Python 2.7.11 |Anaconda 2.5.0 (64-bit)| (default, Dec 6 2015, 18:08:32) [GCC 4.4.7 20120313 (Red Hat 4.4.7-1)]


回答1:


now in Sept 2019 this code works:

import matplotlib.pyplot as plt
import sympy

x, y = sympy.symbols('x y')

plt.ion() #interactive on 

p1 = sympy.plot_implicit(sympy.Eq(x**2 +y**2, 4), block = False)

fg, ax = p1._backend.fig, p1._backend.ax  # get matplotib's figure and axes

# Use matplotlib to change appearance:
ax.axis('tight')  # list of float or {‘on’, ‘off’, ‘equal’, ‘tight’, ‘scaled’, ‘normal’, ‘auto’, ‘image’, ‘square’}
ax.set_aspect("equal") # 'auto', 'equal' or a positive integer is allowed
ax.grid(True)
plt.ioff() #interactive off
plt.show()



回答2:


I'm not sure if this is covered in Sympy's stable API, but you can extract matplotlib's figure and axis instance and the use standard matplotlib calls to change the appearance of your plot:

import matplotlib.pyplot as plt
import sympy as sy

x, y = sy.symbols('x y')
p1 = sy.plot_implicit(sy.Eq(x**2 +y**2, 4))
fg, ax = p1._backend.fig, p1._backend.ax  # get matplotib's figure and ax

# Use matplotlib to change appearance: 
ax.axis('tight')  # list of float or {‘on’, ‘off’, ‘equal’, ‘tight’, ‘scaled’, ‘normal’, ‘auto’, ‘image’, ‘square’}
ax.set_aspect("equal") # 'auto', 'equal' or a positive integer is allowed
ax.grid(True)
fg.canvas.draw()


plt.show()  # enter matplotlib's event loop (not needed in Jupyter)

This gives:




回答3:


Within the help for plot_implicit, the x_var and y_var-arguments are mentioned. Using them allows you to manually set limits to the x and y axis. If you scale those limits appropriately, you can achieve an even aspect ratio.

from sympy import *

x, y = symbols('x y')

scal = 3840/2400 # corresponds to your screen resolution
a = 1.05

p1 = plot_implicit(Eq(x**2+y**2,1),title='with xlim and ylim\n',\
                   xlim=(-1,1), ylim=(-1,1),aspect_ratio='equal')

p2 = plot_implicit(Eq(x**2+y**2,1),title='with x_var and y_var\n',\
                   x_var=(x,-a*scal,a*scal), y_var=(y,-a,a))

(My Sympy-version: 1.1.1)



来源:https://stackoverflow.com/questions/36505768/in-sympy-plotting-how-can-i-get-a-plot-with-a-fixed-aspect-ratio

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!