Lindenmayer ด้วย Python

  • warning: realpath() [function.realpath]: SAFE MODE Restriction in effect. The script whose uid is 1005 is not allowed to access /tmp owned by uid 0 in /var/www/sites/sugree/codenone.com/subdomains/www/html/includes/file.inc on line 190.
  • warning: realpath() [function.realpath]: SAFE MODE Restriction in effect. The script whose uid is 1005 is not allowed to access /tmp owned by uid 0 in /var/www/sites/sugree/codenone.com/subdomains/www/html/includes/file.inc on line 190.

โจทย์ - http://www.codenone.com/node/242

โชคดี Python มี turtle ในตัว

#!/usr/bin/env python
 
import turtle
 
class Turtle:
    def __init__(self,**kw):
        self.axiom = kw.get('axiom','B')
        self.rules = kw.get('rules',[])
        self.angle = kw.get('angle',20)
        self.initial_length = kw.get('initial_length',20)
        self.speed = kw.get('speed','normal')
        self.state = []
 
    def substitute(self,s,depth):
        for i in range(depth):
            for src,dest in self.rules:
                s = s.replace(src,dest)
        return s
 
    def save_state(self):
        self.state.append((turtle.position(),turtle.heading(),self.current_length))
 
    def restore_state(self):
        pos,angle,length = self.state.pop()
        turtle.up()
        turtle.goto(pos)
        turtle.setheading(angle)
        turtle.down()
        self.current_length = length
 
    def handle_cmd(self,c):
        if c == 'B':
            pass
        elif c == 'F':
            turtle.forward(self.current_length)
        elif c == 'G':
            turtle.up()
            turtle.forward(self.current_length)
            turtle.down()
        elif c == '+':
            turtle.right(self.angle)
        elif c == '-':
            turtle.left(self.angle)
        elif c == '[':
            self.save_state()
        elif c == ']':
            self.restore_state()
        elif c == '|':
            self.current_length = int(self.current_length*0.65)
            turtle.forward(self.current_length)
 
    def interpret(self,s):
        self.current_length = self.initial_length
        for c in s:
            self.handle_cmd(c)
 
    def run(self,depth=1):
        turtle.reset()
        turtle.setheading(90)
        turtle.speed(self.speed)
        s = self.substitute(self.axiom,depth)
        print s
        self.interpret(s)
        turtle.done()

ตอนใช้ต้องบอกพารามิเตอร์ โดยเฉพาะอย่างยิ่ง rules และ initial length

tree = {
    'axiom': 'B',
    'rules': [('B','F[-B]+B'),('F','FF')],
    'angle': 20,
    'initial_length': 5,
    'speed': 'fastest',
}
 
tree2 = {
    'axiom': 'F',
    'rules': [('F','|[-F]|[+F]F'),],
    'angle': 25,
    'initial_length': 150,
    'speed': 'fastest',
}
 
depth = 20
t = Turtle(**tree2)
t.run(depth)

ย้าย Codenone

ประกาศย้าย Codenone ไปใช้ Forum ของ Blognone แทนครับ ตามไปตั้งกระทู้ต่อได้ที่ Codenone Forum (รายละเอียดอ่านจากกระทู้ ย้าย Codenone ไปรวมกับ Blognone)

กระทู้เก่าๆ จะย้ายตามไปในภายหลัง ตอนนี้ปิดการโพสต์กระทู้ไว้ เหลือไว้เฉพาะอ้างอิงเท่านั้น