PythonでLisp(S式)パーサ その1

[pukiwiki]
先に一行ニュース
*[[ググる:ピエゾフィルム スピーカー]]
Emorningに登場したセンサー素材 「ピエゾフィルム」
逆に、電気を流すと、無職透明で極薄のスピーカーにもなるみたいです!?

*[[スタートレックな壁紙:http://www.ohgizmo.com/2009/04/07/turn-your-room-into-the-starship-enterprise/]]
$187なり。円安になったから、1万9千円弱?

*[[仮面ライダー新1号変身ベルト(島本和彦):http://simamotoblog.zenryokutei.com/?eid=949964]]
オチで噴きました。
—-
*PythonでLisp(S式)解析
他の作業をしなきゃいけないので、とりあえず出来たところまでメモ。

[/pukiwiki]

—-

PythonでS式を解析するコードを書いたのは、世界で何千人目(何万人目?)だろうと思いつつ。。。
あとで、他の人の記事を漁りますー

import re
import sys

symboldict = dict(
    LBracket=r"(?P<LBracket>\()",
    RBracket=r"(?P<RBracket>\))",
    Blank=r"(?P<Blank>[\s\n]+)",
    Symbol=r"(?P<Symbol>[a-zA-Z_]+\w*)",
    Int=r"(?P<Int>[-]?\d+)",
    Float=r"(?P<Float>[\+-]?\d+\.*\d*([eE]+[+-]?\d+)?)",
    Quote=r"(?P<Quote>\')",
)
anytoken=re.compile("("+"|".join(symboldict.values())+")")


class SpecialForm(object):
    def __init__(self,name):
        self.name=name
    def __repr__(self):
        return "%s"%self.name

class SpecialFormList(list):
    def __init__(self,namelist=[]):
        for x in namelist:
            self.append(x)
    def append(self,x):
        list.append(self,x)
        self.__dict__[x]=SpecialForm(x)
        
sp=SpecialFormList()
sp.append("quote")

class Parser(object):
    def __init__(self):        
        self.init()
        self.switch=dict(
            LBracket=self.LBracket,
            RBracket=self.RBracket,
            Blank=self.Blank,
            Symbol=self.Symbol,
            Int=self.Int,
            Float=self.Float,
            Quote=self.Quote,
        )
    def init(self):
        self._root=[]
        self._list=[self._root]
    def parse(self,txt):
        anytoken.sub(self.callback,txt)

    def callback(self,x ):
        d=x.groupdict()
        stat=[k for k in d if d[k]][0]
        v=d[stat]
        #print stat,v
        self.switch[stat](v)

    def LBracket(self,v):
        mylist=[]
        self._list[-1].append(mylist)
        self._list.append(mylist)        
    def RBracket(self,v):
        self._list.pop()
    def Symbol(self,v):
        self._list[-1].append(v)
    def Quote(self,v):
        self._list[-1].append(sp.quote)
    def Float(self,v):
        self._list[-1].append(float(v))
    def Int(self,v):
        self._list[-1].append(int(v))
    def Blank(self,v):
        pass


if __name__=="__main__":
    txt="""(\'abc (i j) 
            (cond
            (x f1)
            (y f2)
            (z f3)))"""
    
    print txt
    p=Parser()
    p.parse(txt)
    print p._root
    """
    result
    [[quote, 'abc', ['i', 'j'], ['cond',
    ['x', 'f1'], ['y', 'f2'], ['z', 'f3']]]]
    """

TODO
・特殊形式の解析のあたりが、まだいい加減。
・まだコードを実行する部分を書いてません
・ドットペア

続きは また今度

コメントを残す

メールアドレスが公開されることはありません。