Upgrade to Pro — share decks privately, control downloads, hide ads and more …

scheme-silver-paren.pdf

Niyarin
September 26, 2019

 scheme-silver-paren.pdf

Niyarin

September 26, 2019
Tweet

More Decks by Niyarin

Other Decks in Programming

Transcript

  1. 実装中のSchemeパッケージマネージャと featuresと マクロ Niyarin

  2. はなすこと ◦前提 ・Schemeの仕様 ・featuresとcond-expand ◦ Package manager “Silver paren” ◦

    R7RSでマクロを書くには ・CPSマクロ
  3. Schemeの仕様1 R7RS ・Schemeの現在主流の仕様 small(コアの部分) :2013- large(たくさんの機能追加): Red(2016) , Tangerine(2019) …

    ・ライブラリとして小分けされている Samll (scheme base) (scheme file) (scheme load) (scheme repl) … Red (scheme list) (scheme sort) (scheme hash-table) … ・基本の(scheme base)ライブラリ以外は提供の選択は自由 → R7RS large以降の処理系ごとの差はさらに広がるかも
  4. Schemeの仕様2 SRFI ・Schemeのライブラリ、言語拡張の仕様(非公式) 。 各機能ごとに番号がつけられている 例:SRFI1 : list ライブラリ  

    SRFI62: S式コメント SRFI106:socketライブラリ いくつかはRnRSにマージされている 例:SRFI1 listライブラリ → R7RS large (scheme list) SRFI62 S式コメント → R7RS small 処理系作者が好きなものを選んでいれる
  5. Schemeのfeatures 処理系の機能をシンボルのリストで持っている > (features) (srfi-111 srfi-106 srfi-95 srfi-60 srfi-43 srfi-26

    srfi-17 srfi-8 srfi-1 srfi-0 r7rs little-endian lp64 x86-64 gnu-linux unix posix ieee-float picrin) ・処理系の名前、バージョン  picrin , gauche , gauche-0.9.8 ・OS環境 windows gnu-linux linux … ・文字コード full-unicode ・ライブラリ r7rs , srfi-111 , ffi , crypto 特に規定はないが、概ね↓のようなものが提供される
  6. Schemeのcond-expand featuresごとに場合分けする (cond-expand (gauche Gaucheに依存したなにか) (sagittarius Sagittariusに依存したなにか) (unix unix環境に依存したなにか )

    (else (error “Sorry”)))
  7. Schemeのcond-expand2 test部にはもう少し複雑なことが書ける (and or not library) (cond-expand ((or unix gnu-linux

    bsd) Unix系に依存したなにか ) ((library (srfi 1)) SRFI1に依存したなにか) ((library (scheme list)) Scheme listに依存したなにか))
  8. パッケージマネージャ ”Silver Paren” ・現在実装中(https://github.com/niyarin/silver-paren) ・特定の処理系に依存しない → R7RSに準拠した処理系でならば動作する ・パッケージの依存+featuresで管理する

  9. Silver Parenでのfeaturesの役割 ・特定の環境用のパッケージが使えるかの確認 OS(windows,unix )や 日本語が使えるか(full-unicode) ・オプション用 featuresで切り替えることで、依存関係を小さくする 例 ・アプリケーションでGUIをサポートするか

  10. Silver Parenでの外部表現 ◦パッケージ名の構造 (package-xxx (features gui full-unicode) (version 1.0)) ◦コマンドライン上での表現

    ・二重引用符で囲ったリスト VS 他の表現 sip gosh install package-xxx :feature gui :feature full-unicode :version 1.0
  11. 実装する上で不足している”標準”Scheme機能1 ・ディレクトリ周りの仕様が存在しない 処理系固有のものは当然ある Gaucheの(file util)やSagitarriusの(util file)など → 特定の処理系に依存しないということに反する R7RS largeに期待する Green

    Docket(非ポータブルなライブラリ群) system command か ディレクトリライブラリのどちらかは入るはず だいぶ先になりそう Red(2016) → Tangerine(2019)→Orange(2022?)→Amber(2025?)→ Yellow(2028?) → Green(2031?)
  12. 実装する上で不足している”標準”Scheme機能2 ・Github上のライブラリをダウンロードしたい 外部コマンドを叩く手段がポータブルに用意されていない → 同じく、Green Docket system command 期待

  13. Scheme内で解決することを諦めた Shell Scriptの中で呼び出して、コマンドを受けとる #!/bin/sh function do_command(){ if [ $cmd =

    "create-dir" ]; then target_dir=`eval "echo $opt"` mkdir $target_dir elif [ $cmd = "restart" ]; then restart fi } function read_loop(){ for output in `$TARGET_SCHEME $SILVER_PAREN_PATH/sip-main.scm $OPT $OUTSOURCING_OPT` do if echo $output|grep "^Silver-paren-out-command:" >/dev/null ; then expression=`echo $output|sed "s/^Silver-paren-out-command://g"`; do_command $expression else echo $output fi done } read_loop
  14. R7RSマクロ1 Schemeのマクロ R7RSのマクロ syntax-rules (define-syntax my-let (syntax-rules () ((_ ((name

    value) ... ) body ... ) ((lambda (name ... ) body ... ) value ... )))) ・高水準マクロ(lisp評価を使わない、別言語 ) R6RS(一つ前の仕様) 、 処理系依存のマクロ syntax-case , implicit-renaming , explicit-renaming , syntactic-lambda など (define-syntax my-let (ir-macro-transformer (lambda (form rename compare) (let ((bindings (cadr form)) (bodies (cddr form))) `((lambda ,(map car bindings) ,@bodies) ,@(map cadr bindings))))))
  15. R7RSマクロ2 syntax-rulesで扱いにくいマクロ (ore-quote (1 (1 2 3 4 5) (6

    7 8 9))) ; → (quote (1 (5 4 3 2 1) (6 7 8 9))) (ore-quote (2 (1 2 3 4 5) (6 7 8 9))) ; → (quote (1 (1 2 3 4 5) (9 8 7 6))) ※quasi-quoteに展開すれば楽だけど。 このようなマクロ ore-quoteを考える 引数のCAR部が1なら次の要素をreverseする 2なら次の次の要素をreverseする
  16. R7RSマクロ3 reverse (define-syntax ore-reverse (syntax-rules () ((_ "INTERNAL" (robj ...)

    ()) (robj ...)) ((_ "INTERNAL" (robj ...) (obj1 obj2 ...)) (ore-reverse "INTERNAL" (obj1 robj ...) (obj2 ...))) ((_ (obj ...)) (ore-reverse "INTERNAL" () (obj ...)))))) 展開 (ore-reverse (1 2 3)) → (ore-reverse “INTERNAL” () (1 2 3)) → (ore-reverse “INTERNAL” (1) (2 3)) → (ore-reverse “INTERNAL” (2 1) (3)) → (ore-reverse “INTERNAL” (3 2 1) ()) → (3 2 1)
  17. R7RSマクロ4 ore-quote(失敗) (define-syntax ore-quote (syntax-rules () ((_ (1 ls1 ls2))

    (quote (1 (ore-reverse ls1) ls2))) ((_ (2 ls1 ls2)) (quote (2 ls1 (ore-reverse ls2)))))) 展開 (ore-quote (1 (1 2 3) (4 5 6))) → (quote (1 (ore-reverse 1 2 3) (4 5 6))) quoteの中はリテラルであってlisp式でないのでこれ以上展開されない
  18. R7RSマクロ5 CPSマクロを使う マクロを展開を内側からできればうまくいく → CPSマクロ 次にすることを明示的に渡すマクロ記述スタイル (define-syntax cps-macro-example (syntax-rules ()

    ((_ 次に展開したいマクロ 引数1 引数2 …) (次に展開したいマクロ 展開結果)))) 例えば、今回のケースだと、reverseした後quoteで囲いたい → reverse-CPSマクロは 次に展開したいマクロである”quoteで囲うマクロ”を受け取る
  19. R7RSマクロ5 CPSマクロの動作 (%reverse (syntax-lambda (it) it) (1 2 3 list))

    →(list 3 2 1) 次になにもすることがない(一番外側)の場合 (%reverse (syntax-lambda (it) (quote (1 it (4 5 6))) (1 2 3)) →(quote (1 (3 2 1) (4 5 6))) quoteで囲う例
  20. R7RSマクロ6 syntax-lambdaとは syntax-lambdaにどうやって結果をいれているのか →syntax-lambdaはマクロの機構ではなく勝手につくっただけ → syntax-lambdaをマクロに変換して適用できるようにする (syntax-rules () ((_ (syntax-lambda

    (c-arg) c-body) 引数 1 引数2 …) (let-syntax ((cont-syntax ;↓syntax-lambdaからマクロに変換 (syntax-rules () ((_ c-arg) c-body)))) (cont-syntax ;変換されたsyntax-lambdaに結果を適用 (結果 …) )))
  21. R7RSマクロ7 %ore-quoteはどうなったのか (define-syntax %ore-quote (syntax-rules (syntax-lambda) ((_ (syntax-lambda (c-arg) c-body)

    (1 ls1 ls2)) (let-syntax ((cont-syntax (syntax-rules () ((_ c-arg) c-body)))) (cont-syntax (%ore-reverse (syntax-lambda (it) (quote (1 it ls2))) ls1)))) ((_ (syntax-lambda (c-arg) c-body)(2 ls1 ls2)) (let-syntax ((cont-syntax (syntax-rules () ((_ c-arg) c-body)))) (cont-syntax (%ore-reverse (syntax-lambda (it) (quote (2 ls1 it))) ls2))))))
  22. R7RSマクロ7 全体 https://gist.github.com/niyarin/87752d24508f63cf8a6eb33a2f43d9ae

  23. 話したこと ・Schemeの仕様について話した ・パッケージマネージャSilver Parenについて ・CPSマクロについて まとめ 年内にはsilver-parenを動くようにしたい