Python turtle 库未提供画抛物线的函数,但可通过解析函数( y 2 = 2 p x y^2=2px y2=2px, x 2 = 2 p y x^2=2py x2=2py)描点连线实现抛物线的绘制。所计算的点越多,图像就越接近抛物线。
# 海龟绘图绘制抛物线
# author: 小喾苦
# date: 2022-5-14
# author's github: https://github.com/xkk1
# author's bilibili: https://space.bilibili.com/513689605
import turtle
if "turtle" not in locals().keys():
turtle = None
def parabola_x(begin, end, step=10, endstart=False, t=turtle):
"""
绘制开口朝向x轴(左右开口)的抛物线 y²=2px 的一半
parabola_x(begin, end, step=10, endstart=False, t=turtle)
begin 开始坐标、抛物线的顶点(x₁,y₁)
end 结束坐标(x₂,y₂)
step 精度,为一个整数,数越小精度越高速度越慢
endstart 是否从结束坐标开始绘制(True是\False否)
t turtle库的名称
"""
p = ( (end[1]-begin[1])**2/abs(end[0]-begin[0]) )/2 # 计算抛物线p的大小
if end[0]-begin[0] < 0: # 确定抛物线p的正负号
p = -p
if begin[1] > end[1]: # 确定精度的正负号
step = -step
t.pu() # 抬笔
if endstart == True: # 如果从结束坐标开始绘制
t.goto(end[0], end[1]) # 前往结束坐标
start = end[1]+1
stop = begin[1]
step = -step
else:
start = begin[1]
stop = end[1]+1
t.goto(begin[0], begin[1]) # 前往初始坐标
t.pd() # 放笔
for y in range(start ,stop ,step): # 相当于画函数图像的列表
x = ((y-begin[1])**2)/(2*p) + begin[0] # 计算x坐标
t.goto(x, y) # 相当于画函数图像的描点、连线
if endstart == True:
t.goto(begin[0], begin[1]) # 前往初始坐标
else:
t.goto(end[0], end[1]) # 前往结束坐标
return None
def parabola_y(begin, end, step=10, endstart=False, t=turtle):
"""
绘制开口朝向y轴(上下开口)的抛物线 x²=2py 的一半
parabola_y(begin, end, step=10, t=turtle)
begin 开始坐标、抛物线的顶点(x₁,y₁)
end 结束坐标(x₂,y₂)
step 精度,为一个整数,数越小精度越高速度越慢
endstart 是否从结束坐标开始绘制(True是\False否)
t turtle库的名称
"""
p = ( (end[0]-begin[0])**2/abs(end[1]-begin[1]) )/2 # 计算抛物线p的大小
if end[1]-begin[1] < 0: # 确定抛物线p的正负号
p = -p
if begin[0] > end[0]: # 确定精度的正负号
step = -step
t.pu() # 抬笔
if endstart == True: # 如果从结束坐标开始绘制
t.goto(end[0], end[1]) # 前往结束坐标
start = end[0]+1
stop = begin[0]
step = -step
else:
start = begin[0]
stop = end[0]+1
t.goto(begin[0], begin[1]) # 前往初始坐标
t.pd() # 放笔
for x in range(start ,stop ,step): # 相当于画函数图像的列表
y = ((x-begin[0])**2)/(2*p) + begin[1] # 计算y坐标
t.goto(x, y) # 相当于画函数图像的描点、连线
if endstart == True:
t.goto(begin[0], begin[1]) # 前往初始坐标
else:
t.goto(end[0], end[1]) # 前往结束坐标
return None
通过调用函数 parabola_x() 绘制左右开口的抛物线,调用函数 parabola_y()绘制上下开口的抛物线。例如:
parabola_y((-400,400), (400,0)) # 绘制以(-400,400)开始(400,0)结束开口朝向下的抛物线
parabola_x((-400,0), (400,-400),step=20 ,endstart=True) # 绘制以(-400,0)开始(400,-400)结束开口朝向右的抛物线(其中每隔20像素横坐标计算一次纵坐标,从结束向起点绘制)
# 海龟绘图绘制数学抛物线
# author: 小喾苦
# date: 2022-5-14
# author's github: https://github.com/xkk1
# author's bilibili: https://space.bilibili.com/513689605
import turtle as t
if "turtle" not in locals().keys():
turtle = None
def parabola_x(begin, end, step=10, endstart=False, t=turtle):
"""
绘制开口朝向x轴(左右开口)的抛物线 y²=2px 的一半
parabola_x(begin, end, step=10, endstart=False, t=turtle)
begin 开始坐标、抛物线的顶点(x₁,y₁)
end 结束坐标(x₂,y₂)
step 精度,为一个整数,数越小精度越高速度越慢
endstart 是否从结束坐标开始绘制(True是\False否)
t turtle库的名称
"""
p = ( (end[1]-begin[1])**2/abs(end[0]-begin[0]) )/2 # 计算抛物线p的大小
if end[0]-begin[0] < 0: # 确定抛物线p的正负号
p = -p
if begin[1] > end[1]: # 确定精度的正负号
step = -step
t.pu() # 抬笔
if endstart == True: # 如果从结束坐标开始绘制
t.goto(end[0], end[1]) # 前往结束坐标
start = end[1]+1
stop = begin[1]
step = -step
else:
start = begin[1]
stop = end[1]+1
t.goto(begin[0], begin[1]) # 前往初始坐标
t.pd() # 放笔
for y in range(start ,stop ,step): # 相当于画函数图像的列表
x = ((y-begin[1])**2)/(2*p) + begin[0] # 计算x坐标
t.goto(x, y) # 相当于画函数图像的描点、连线
if endstart == True:
t.goto(begin[0], begin[1]) # 前往初始坐标
else:
t.goto(end[0], end[1]) # 前往结束坐标
return None
def parabola_y(begin, end, step=10, endstart=False, t=turtle):
"""
绘制开口朝向y轴(上下开口)的抛物线 x²=2py 的一半
parabola_y(begin, end, step=10, t=turtle)
begin 开始坐标(x₁,y₁)
end 结束坐标(x₂,y₂)
step 精度,为一个整数,数越小精度越高速度越慢
endstart 是否从结束坐标开始绘制(True是\False否)
t turtle库的名称
"""
p = ( (end[0]-begin[0])**2/abs(end[1]-begin[1]) )/2 # 计算抛物线p的大小
if end[1]-begin[1] < 0: # 确定抛物线p的正负号
p = -p
if begin[0] > end[0]: # 确定精度的正负号
step = -step
t.pu() # 抬笔
if endstart == True: # 如果从结束坐标开始绘制
t.goto(end[0], end[1]) # 前往结束坐标
start = end[0]+1
stop = begin[0]
step = -step
else:
start = begin[0]
stop = end[0]+1
t.goto(begin[0], begin[1]) # 前往初始坐标
t.pd() # 放笔
for x in range(start ,stop ,step): # 相当于画函数图像的列表
y = ((x-begin[0])**2)/(2*p) + begin[1] # 计算y坐标
t.goto(x, y) # 相当于画函数图像的描点、连线
if endstart == True:
t.goto(begin[0], begin[1]) # 前往初始坐标
else:
t.goto(end[0], end[1]) # 前往结束坐标
return None
# 示例
t.setup(850,850) # 设置屏幕大小
t.title("Python turtle海龟绘图绘制数学抛物线 by 小喾苦") # 设置窗口标题
t.pensize(5) # 设置画笔粗细
#画坐标轴
t.speed(10) # 设置画笔速度
def draw_axis(string=""):
"画一个做坐标轴"
t.fd(400)
t.rt(90)
t.pu()
t.fd(40)
t.write(string, font=("Arial", 20, "normal"))
t.bk(40)
t.pd()
t.lt(90)
t.lt(135)
t.fd(20)
t.bk(20)
t.lt(90)
t.fd(20)
t.bk(20)
t.rt(45)
t.fd(800)
t.bk(400)
t.rt(180)
draw_axis("X") # 画x轴
t.lt(90)
draw_axis("y") # 画y轴
t.lt(135)
t.pu()
t.fd(40)
t.write("o", font=("Arial", 20, "normal")) # 标原点
# 画抛物线
t.speed(6) # 设置画笔速度
t.pencolor("blue") # 设置画笔颜色
parabola_y((0,0), (-400,400), endstart=True,t=t) # 绘制开口朝向y轴的抛物线
parabola_y((0,0), (400,400),t=t) # 绘制开口朝向y轴的抛物线
t.pencolor("red") # 设置画笔颜色
parabola_x((0,0), (400,400), step=20 ,endstart=True,t=t) # 绘制开口朝向x轴的抛物线
parabola_x((0,0), (400,-400), step=20 ,t=t) # 绘制开口朝向x轴的抛物线
t.done() # 开始事件循环
附 Python turtle 官方文档链接 https://docs.python.org/zh-cn/3.8/library/turtle.html