Archive for 2014年12月|Monthly archive page
FOOP で DAG する
前回の DAG スクリプトは如何だったでしょうか?
search-XXX なんて関数名は有りがちな名前。そんな時、関数名の衝突を避けるには FOOP(Functional-Object Oriented Programming )なんてもってこい。
とは言え、newLISP の目玉でもある FOOP を使ってこなかった私。この辺で覚書きでも作っておこうかと、、、
ということで、コードは、
(new Class 'MAIN:DAG)
(define (DAG:DAG lst)
(list DAG lst))
(define (DAG:nodes)
(self 1))
(define (DAG:search-pre)
(letex (_x (args 0))
(if (find-all '(? _x) (self 1)) $it "start")))
(define (DAG:search-next)
(letex (_x (args 0))
(if (find-all '(_x ?) (self 1)) $it "end")))
(define (DAG:search-all)
(letex (_x (args 0))
(local (res)
(dolist (x (self 1))
(if (match '(? _x) x) (push x res -1)
(match '(_x ?) x) (push x res -1)))
res)))
ポイントは、オブジェクト・データ部分のアクセスが self になること。
とわかっていても、私には慣れが必要かも。引数の扱いが、、、
さて、使い方は、
> (set 'mydag (DAG '((a c) (b c) (c d) (c g) (d e) (d f)))) (DAG ((a c) (b c) (c d) (c g) (d e) (d f))) > (:nodes mydag) ((a c) (b c) (c d) (c g) (d e) (d f)) > (:search-all mydag 'd) ((c d) (d e) (d f)) > (:search-pre mydag 'd) ((c d)) > (:search-next mydag 'd) ((d e) (d f)) > (:search-pre mydag 'a) "start" > (:search-next mydag 'g) "end" >
こんな感じ。
以上、如何でしょうか?
newLISP で DAG する...または、match な find-all
DAG (Directed acyclic graph) とは有向非巡回グラフのことらしい。
といっても、DAG が何かわからずにコードを書いた私。
きっかけは、newLISP Foram の投稿から。
これは簡単にコード化はできそうだと思い、書いて投降したのですが、、、
何か、しっくりこなかったのです。newLISP らしくないというか、、、
同投稿で rickyboy 氏が find に match を使っているのを見て、思い出しました。 find-all がリストに対して match になる(第二構文)ことを。
(if (replace nil (map (fn (x) (match '(? _x) x true)) lst)) $it "start")
なんて、長ったらしいコードは、find-all を使えば、
(if (find-all '(? _x) lst) $it "start")
ああ、すっきり。
前にも、こんなことがあったのを思い出し、忘れないよう blog に(笑)
先に newLISP Foram に投降したコードは、こんな感じに変わります。
(define (search-pre lst)
(letex (_x (args 0))
(if (find-all '(? _x) lst) $it "start")))
(define (search-next lst)
(letex (_x (args 0))
(if (find-all '(_x ?) lst) $it "end")))
(define (search-all lst)
(letex (_x (args 0))
(local (res)
(dolist (x lst)
(if (match '(? _x) x) (push x res -1)
(match '(_x ?) x) (push x res -1)))
res)))
ついでに newLISP らしく、if の cond 的な使い方も(笑)
以上、如何でしょうか?