- 1. 绘制谢尔宾斯基三角形(正三角形)
- 2. 绘制谢尔宾斯基三角形(倾斜三角形)
- 3. 递归输出列表
定义:
谢尔宾斯基三角形(英语:Sierpinski triangle)是一种分形,
由波兰数学家谢尔宾斯基在1915年提出.
参考:百度百科
谢尔宾斯基三角形
参考图谢尔宾斯基三角形,分别写两py程序,实现图中两三角形的绘制
图一为:
思路:
首先先定义好画画的方法,我们将需要画的点坐标和颜色传入draw方法中,然后记得一开始要把penup,也就是把笔提起来,要不然就会画下画笔的移动鬼姬.
再定义一个获取两坐标中间位置的坐标的方法,getMid.
我们主要是使用turtle这个库来实现了,方法为使用递归嵌套,每次使degree减一来完成递归 *** 作.每次都把三个顶点的坐标减半.
(当然颜色你是可以根据自己的喜好来的hh)
图一三角形代码区:
import turtle
def draw(points, color):
t.fillcolor(color)
t.penup() # 提起画笔,防止将画笔移动的路劲给画下来
t.goto(points['left'])
t.pendown() # 开始画
t.begin_fill()
t.goto(points['top'])
t.goto(points['right'])
t.goto(points['left'])
# 以左上右下的顺序进行画三角形。
t.end_fill()
def getMid(p1, p2):
return (p1[0] + p2[0]) / 2, (p1[1] + p2[1]) / 2
# 获得两点之间的点
def sierpinski(degree, points):
colors = ["blue", "red", "green", "white", "yellow", "pink", "orange"]
if degree > 0:
draw(points, colors[degree - 1])
# 根据不同的层数来选择不同的颜色
sierpinski(degree - 1, {'left': points['left'], 'top': getMid(points['left'], points['top']),
'right': getMid(points['left'], points['right'])})
# 递归调用,实现每次都画一个边长只有原来一半的三角形
sierpinski(degree - 1, {'left': getMid(points['left'], points['top']), 'top': points['top'],
'right': getMid(points['top'], points['right'])})
sierpinski(degree - 1,
{'left': getMid(points['left'], points['right']), 'top': getMid(points['top'], points['right']),
'right': points['right']})
t = turtle.Turtle()
t.speed(30) # 速度可以自己设置,不过小了会很慢
points = {'left': (-200, -100), 'top': (0, 200), 'right': (200, -100)}
# 起始位置,因为最中间时(0,0)。所以我们这样设置
sierpinski(7, points) # 有7层
turtle.done()
最后我自己运行的效果:
图二:
图二要实现:
思路:
其实很简单,就是把上面实现的稍微改一下,把顶点的位置往右移动一点就不是正三角形了,然后再把配色改一下就ok了
图二三角形代码区:
import turtle
def draw(points, color):
t.fillcolor(color)
t.penup()
t.goto(points['left'])
t.pendown()
t.begin_fill()
t.goto(points['top'])
t.goto(points['right'])
t.goto(points['left'])
t.end_fill()
def getMid(p1, p2):
return (p1[0] + p2[0]) / 2, (p1[1] + p2[1]) / 2
def sierpinski(degree, points):
if degree > 1:
draw(points, "black")
#因为我们要实现的图片是黑色底的,只有在最后一层的时候才画黄色的三角形,所以这里进行判断,然后再选择不同的颜色进行填充
sierpinski(degree - 1, {'left': points['left'], 'top': getMid(points['left'], points['top']),'right': getMid(points['left'], points['right'])})
sierpinski(degree - 1, {'left': getMid(points['left'], points['top']), 'top': points['top'],'right': getMid(points['top'], points['right'])})
sierpinski(degree - 1,{'left': getMid(points['left'], points['right']), 'top': getMid(points['top'], points['right']), 'right': points['right']})
if degree == 1:
draw(points, "yellow")
sierpinski(degree - 1, {'left': points['left'], 'top': getMid(points['left'], points['top']), 'right': getMid(points['left'], points['right'])})
sierpinski(degree - 1, {'left': getMid(points['left'], points['top']), 'top': points['top'], 'right': getMid(points['top'], points['right'])})
sierpinski(degree - 1, {'left': getMid(points['left'], points['right']), 'top': getMid(points['top'], points['right']), 'right': points['right']})
t = turtle.Turtle()
t.speed(30)
#因为这次是倾斜的三角形而不是等边三角形,所以把top点稍微歪一点就可以实现
points = {'left': (-200, -100), 'top': (50, 200), 'right': (200, -100)}
sierpinski(6, points)
turtle.done()
最后我自己的实现效果图:
3. 递归输出列表
写一个print_list函数,实现同print函数相似的功能。
要求代码中不出现for、while。
也不能这样:
def print_list(lst):
print(lst)
(递归实现)
思路:
因为不能使用for while所以我们可以使用递归切片来进行输出每次列表的第一个元素,然后将从第二个元素开始的新列表传给本身函数进行递归,从而实现输出每一个元素
数字部分我们已经完成了,但是还有中括号部分需要完成,首先因为我们是用递归做的,所以如果直接输出中括号的话会出现很多个,那么要怎么才可以实现在递归函数中是的某些代码只运行一次呢?
我们可以使用全局变量和进行条件判断的方法.
对于前括号,我们使用全局变量来进行控制,一旦发现是第一次运行,就加上一个[,要不然都不加[直接输出首元素.
后括号我们使用条件来进行控制,当长度为1的时候就输出元素和]结尾.
当然因为列表还有很多特殊情况都是需要考虑的,比如列表为空,那么我们就当长度为0时输出[]就可以了.
代码区:
f = 1#全局变量f,f=1代表是第一次运行print_list方法
def print_list(lst):
global f
if len(lst) == 0:
print([])
elif len(lst) == 1:
if f == 1:
print(f"[{lst[0]}]")
else:
f = 1
print(f"{lst[0]}]")
else:
if f == 1:
print(f"[{lst[0]}", end=', ')
f += 1
print_list(lst[1:])
else:
print(lst[0], end=', ')
print_list(lst[1:])
def main():
print([1, 22, 555])
print_list([1, 22, 555])
print([])
print_list([])
print([521])
print_list([521])
main()
新手上路,有错请指正;
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)