2016-07-14 8 views
1

} {begin}キーワードを置き換えるために、中括弧{{}を使用して文ブロックを指定することは可能ですか?そのため、代わりに:我々が使用することラケットの 'begin'を{}で置き換える中括弧{

(if (condition) 
    (begin 
     (statement1) 
     (statement2) 
     (statement3) 
     (statement4)) 
    (else-statement)) 

(if (condition) { 
     (statement1) 
     (statement2) 
     (statement3) 
     (statement4) } 
    (else-statement)) 

はどのようにこれをaccompalishedすることができますか?あなたの答えをありがとう。

答えて

5

これは完全に可能であり、いくつかの方法があります。 (私が開始する前に、クイックノートでは、私はそれが内部の定義とのより良い動作しますので、blockの代わりbeginを使用するつもりです。)

ワンややハック - yの方法は、カーリーブレースが扱われるようにすることを意味するものを機能アプリケーションを再定義することです特別に。あなたは#%appマクロを定義することによってこれを行うことができます。

#lang racket 
(require racket/block syntax/parse/define (prefix-in - racket)) 
;; This #%app macro redefines what function application means so that 
;; { def-or-expr ... } expands into (block def-or-expr ...) 
;; Otherwise it uses normal function application 
(define-syntax-parser #%app 
    [{_ def-or-expr:expr ...} 
    #:when (equal? #\{ (syntax-property this-syntax 'paren-shape)) 
    ;; group them in a block 
    #'(block def-or-expr ...)] 
    [(_ f:expr arg ...) 
    #:when (not (equal? #\{ (syntax-property this-syntax 'paren-shape))) 
    ;; expand to the old #%app form, from (prefix-in - racket) 
    #'(-#%app f arg ...)]) 
;; using it: 
(define (f x) 
    (if (< 5 x) { 
     (define y (- x 5)) 
     (f y) 
     } 
     x)) 
(f 1) ; 1 
(f 5) ; 5 
(f 6) ; 1 
(f 10) ; 5 
(f 11) ; 1 

もう一つの方法は、新しい#lang言語を定義し、{文字の異なるエントリとreadtableを拡張することです。私に行こうとしましょう...

#lang言語を定義するには、読者の実装をyour-language/lang/reader.rktにする必要があります。ここにはcurly-block/lang/reader.rktがあり、curly-blockディレクトリが1つのコレクションパッケージとしてインストールされています。

;; s-exp syntax/module-reader is a language for defining new languages. 
#lang s-exp syntax/module-reader 
racket 
#:wrapper1 (lambda (th) 
      (parameterize ([current-readtable (make-curly-block-readtable (current-readtable))]) 
       (th))) 

;; This extends the orig-readtable with an entry for `{` that translates 
;; { def-or-expr ... } into (block def-or-expr ...) 
(define (make-curly-block-readtable orig-readtable) 
    (make-readtable orig-readtable 
    #\{ 'terminating-macro curly-block-proc)) 

;; This is the function that the new readtable will use when in encounters a `{` 
(define (curly-block-proc char in src ln col pos) 
    ;; This reads the list of things ending with the character that closes `char` 
    ;; The #f means it uses the racket reader for the first step, so that `{` 
    ;; uses the normal behavior, grouping expressions into a reader-level list 
    (define lst (read-syntax/recursive src in char #f)) 
    (cons 'block lst)) 

は、それを使用する:

#lang curly-block 
(require racket/block) 
(define (f x) 
    (if (< 5 x) { 
     (define y (- x 5)) 
     (f y) 
     } 
     x)) 
(f 1) ; 1 
(f 5) ; 5 
(f 6) ; 1 
(f 10) ; 5 
(f 11) ; 1 
関連する問題