- def parse(line)
- s = line.scan(/\(|\)|"(?:\\.|[^"])*"|[^()" \n]+/)
- f = ->(t=nil){
- case x = t || s.shift
- when ?(
- y = []
- while x = s.shift
- return y if x==?)
- y << f[x]
- end
- fail ")?"
- when nil
- nil
- when /^#(.*)$/
- {?t=>true,?f=>false}[$~[1]]
- when /\d+/
- x.to_i
- when /^\"(.*)\"$/m
- $~[1].gsub(/\\./,'\n'=>"\n","\\\\"=>"\\","\\\""=>'"')
- else
- x.to_sym
- end
- }
- f[]
- end
- $tests = {
- "" => nil,
- "1" => 1,
- "(a b)" => [:a,:b],
- "(1 2(2 3))" => [1,2,[2,3]],
- '(a"b"c"d"(ef))' => [:a,"b",:c,"d",[:ef]],
- '("a b" (c d-e))' => ["a b",[:c,:"d-e"]],
- "(\"a\nb\"\nb\nc (d))" => ["a\nb",:b,:c,[:d]],
- ' "a\nb"' => "a\nb",
- '"a\\"b"'=>'a"b',
- "\"\\\\\""=> "\\",
- "(#t #f)" => [true,false],
- "(define (f x) (if (zero? x) 0 (+ x (f (- x 1)))))" =>
- [:define,[:f,:x],[:if,[:zero?,:x],0,[:+,:x,[:f,[:-,:x,1]]]]],
- }
- p $tests.all?{|x,y|parse(x)==y}
来源: http://www.phpxs.com/code/1006710/