Python 中的指数图而不使用 NumPy
Exponential graphs in Python without using NumPy
我是 python 的新手,我想在不使用 NumPy 的情况下在同一轴上绘制 3 个指数函数(不允许)。允许使用 MatPlotLib、SymPy 等。
问题在下面有广泛的回答。
出于隐私原因删除了代码 - 不需要理解下面的答案,因为它们很宽泛,也不需要回答未来关于此主题的任何问题
这是一种使用 sympy、Python 的符号数学包的方法。它首先将 x* 求解为 log(delta/2)/a
。然后,对于一些给定的值,绘制了一个图。
请注意,sympy 具有非常简化的绘图功能,对图例放置等的控制有限。如果您需要更多控制,则需要在数组中计算函数值。
from sympy import *
from sympy.abc import x, a, b
delta = symbols('delta', real=True)
x_star = symbols('x*', real=True)
f = exp(a*x)
g = -exp(a*x)
h = exp(a*x)*sin(b*x)
eq = Eq(delta, f.subs(x, x_star) - g.subs(x, x_star))
sol = solve(eq, x_star) # [log(delta/2)/a]
values = {a: 0.5, b: 1.5, delta:4.0}
x_star = sol[0].subs(values)
p = plot(f.subs(values), g.subs(values), h.subs(values), (x, 0, x_star),
show=False, legend=True, ylabel='', ylim=(-2,3.5))
p[0].line_color = 'r'
p[1].line_color = 'g'
p[2].line_color = 'b'
p.show()
结果图:
当然,我希望你能理解我的顾虑,我更愿意在尽量帮助你的同时让我的回答尽可能通用。
如果您不能使用 Numpy1, you have to use the math 模块和旧的好列表。
您开始从标准库导入 math
并从 Matplotlib:
导入 pyplot
模块
import math
import matplotlib.pyplot as plt
您决定绘制函数的间隔以及绘图需要多少点
x_0, x_N = 0, 12
N =120
N
最适合作为 N+1 点之间的间隔数,因此我们写成
dx = (x_N-x_0)/N
现在我们可以说 x_i = x_0 + dx × i
但我们必须存储我们的结果以便它们可以重复使用。现在我们必须使用一个列表,我们有两个选择,①从一个空列表开始,然后 append
使用 for
循环
到所有 x_i
xs = []
for i in range(N+1): xs.append(x_0+dx*i)
和②列表理解
xs = [ x_0+dx*i for i in range(N+1) ]
(结果相同)
你现在已经解决了横坐标的问题,轮到纵坐标了;同样,我们可以使用 append
或列表理解
ys = []
for i in range(N+1):
x = xs[i]
y = math.sin(x/3.805)
ys.append(y)
或
ys = [ math.sin(xs[i]/3.805) for i in range(N+1) ]
现在您可以绘制函数了
plt.plot(xs, ys, label='sin(%.3fx)'%(1/3.805))
plt.legend()
plt.grid()
plt.show()
(1) 你不能使用 Numpy 但是,但是 Matplotlib 会在幕后使用 Numpy...
您传递给 plt.plot
的列表 立即 转换为 Numpy 数组!之后才由绘图模块的复杂机器处理。
这是您的版本,经过一些小的调整使其可以正常工作。请注意,matplotlib 的绘图函数与 sympy 的有点不同。
import matplotlib.pyplot as plt
from math import exp, sin
a = 5.0
b = 10.0
d = 0.1
x_star = 6.0
#x_star =(1/a)*float((math.log1p(d/2)))# #x* evenually needs to be in this form*#
print('x*= ',x_star)
steps = 200; r = [i*x_star/steps for i in range(steps)] # similar to np.linspace
f_r = []
g_r = []
h_r = []
for x in r:
y = exp(a*x)
f = y
f_r.append(f)
print('f(x)= ',f)
g = -1*y
g_r.append(g)
print('g(x)= ',g)
h = y*sin(b*x)
h_r.append(h)
print('h(x)= ',h)
plt.plot(r, f_r, 'b--', linewidth=1, color='r', label='f(x)=exp(a*x)')
plt.plot(r, g_r, 'b--', linewidth=2, color='g', label='g(x)=-exp(a*x)')
plt.plot(r, h_r, 'b--', linewidth=3, color='b', label='h(x)=exp(a*x)*sin(b*x)')
plt.ylabel('values')
plt.xlabel('x')
plt.legend(title='functions')
plt.show()
我是 python 的新手,我想在不使用 NumPy 的情况下在同一轴上绘制 3 个指数函数(不允许)。允许使用 MatPlotLib、SymPy 等。
问题在下面有广泛的回答。
出于隐私原因删除了代码 - 不需要理解下面的答案,因为它们很宽泛,也不需要回答未来关于此主题的任何问题
这是一种使用 sympy、Python 的符号数学包的方法。它首先将 x* 求解为 log(delta/2)/a
。然后,对于一些给定的值,绘制了一个图。
请注意,sympy 具有非常简化的绘图功能,对图例放置等的控制有限。如果您需要更多控制,则需要在数组中计算函数值。
from sympy import *
from sympy.abc import x, a, b
delta = symbols('delta', real=True)
x_star = symbols('x*', real=True)
f = exp(a*x)
g = -exp(a*x)
h = exp(a*x)*sin(b*x)
eq = Eq(delta, f.subs(x, x_star) - g.subs(x, x_star))
sol = solve(eq, x_star) # [log(delta/2)/a]
values = {a: 0.5, b: 1.5, delta:4.0}
x_star = sol[0].subs(values)
p = plot(f.subs(values), g.subs(values), h.subs(values), (x, 0, x_star),
show=False, legend=True, ylabel='', ylim=(-2,3.5))
p[0].line_color = 'r'
p[1].line_color = 'g'
p[2].line_color = 'b'
p.show()
结果图:
当然,我希望你能理解我的顾虑,我更愿意在尽量帮助你的同时让我的回答尽可能通用。
如果您不能使用 Numpy1, you have to use the math 模块和旧的好列表。
您开始从标准库导入 math
并从 Matplotlib:
pyplot
模块
import math
import matplotlib.pyplot as plt
您决定绘制函数的间隔以及绘图需要多少点
x_0, x_N = 0, 12
N =120
N
最适合作为 N+1 点之间的间隔数,因此我们写成
dx = (x_N-x_0)/N
现在我们可以说 x_i = x_0 + dx × i
但我们必须存储我们的结果以便它们可以重复使用。现在我们必须使用一个列表,我们有两个选择,①从一个空列表开始,然后 append
使用 for
循环
x_i
xs = []
for i in range(N+1): xs.append(x_0+dx*i)
和②列表理解
xs = [ x_0+dx*i for i in range(N+1) ]
(结果相同)
你现在已经解决了横坐标的问题,轮到纵坐标了;同样,我们可以使用 append
或列表理解
ys = []
for i in range(N+1):
x = xs[i]
y = math.sin(x/3.805)
ys.append(y)
或
ys = [ math.sin(xs[i]/3.805) for i in range(N+1) ]
现在您可以绘制函数了
plt.plot(xs, ys, label='sin(%.3fx)'%(1/3.805))
plt.legend()
plt.grid()
plt.show()
(1) 你不能使用 Numpy 但是,但是 Matplotlib 会在幕后使用 Numpy...
您传递给 plt.plot
的列表 立即 转换为 Numpy 数组!之后才由绘图模块的复杂机器处理。
这是您的版本,经过一些小的调整使其可以正常工作。请注意,matplotlib 的绘图函数与 sympy 的有点不同。
import matplotlib.pyplot as plt
from math import exp, sin
a = 5.0
b = 10.0
d = 0.1
x_star = 6.0
#x_star =(1/a)*float((math.log1p(d/2)))# #x* evenually needs to be in this form*#
print('x*= ',x_star)
steps = 200; r = [i*x_star/steps for i in range(steps)] # similar to np.linspace
f_r = []
g_r = []
h_r = []
for x in r:
y = exp(a*x)
f = y
f_r.append(f)
print('f(x)= ',f)
g = -1*y
g_r.append(g)
print('g(x)= ',g)
h = y*sin(b*x)
h_r.append(h)
print('h(x)= ',h)
plt.plot(r, f_r, 'b--', linewidth=1, color='r', label='f(x)=exp(a*x)')
plt.plot(r, g_r, 'b--', linewidth=2, color='g', label='g(x)=-exp(a*x)')
plt.plot(r, h_r, 'b--', linewidth=3, color='b', label='h(x)=exp(a*x)*sin(b*x)')
plt.ylabel('values')
plt.xlabel('x')
plt.legend(title='functions')
plt.show()