GaucheはR7RS Schemeのパーザをいくつかの点で拡張しています。 また、歴史的経緯から、デフォルトの字句構文の中に、R7RSの仕様と相反するものが いくつかあります。リーダのモードを設定することで、 R7RS互換にすることもできます。
#!で始まるトークンはリーダに特別な影響を与えます。
R7RSではそういった指示子がふたつ定義されています。
シンボルのリード時に大文字小文字を無視するかしないかを
切り替える、#!fold-caseと#!no-fold-caseです。
Gaucheで使える指示子の一覧については、下のHash-bangトークンを参照してください。
Gaucheは、R6RSの[]を()と同様に扱う構文規則を採用しています。
どちらの括弧も全く等価ですが、それぞれの開き括弧と閉じ括弧は対応していなければなりません。
括弧を混ぜることに眉をひそめる熟練のLisperもいますが、
括弧の種類を使い分けるのは、括弧の役割を視覚的に識別するのに役に立ちます。
一般的な慣習は、関数とマクロ呼び出し以外のグルーピングには[]を使う、
というものです。ただしそのようなグルーピングがネストする場合は、外側には()を
使います。例:
(cond [(test1 x) (y z)]
[(test2 x) (s t)]
[else (u v)])
(let ([x (foo a b)]
[y (bar c d)])
(baz x y))
この記法は、必ず従わなければいけないというものではありません。
R7RSではこの構文を採用せず、[]は言語拡張用に取ってあるので、
ポータブルなR7RSプログラムを書く場合は()だけを使うのが良いでしょう。
(リーダがstrict-r7モードの時は、[]が使われていたら
エラーが通知されます。詳しくはリーダー字句モード参照。)
エディタのSchemeモードの中には、)をタイプするとそれがどちらの
種類の括弧を閉じるかに応じて自動的に]か)を選んで挿入してくれる
ものがあります (EmacsのQuackなど)。この記法を使うときは
そういったモードを活用すると良いでしょう。
シンボル名はデフォルトで大文字小文字を区別します (大文字小文字の区別参照)。
数字や’+’, ’-’ で始まるシンボル名も、
トークンが有効な数値リテラルを構成しない限り許されます。
また、他の変な文字も ’|’ でシンボルを囲むことによってシンボル名に含めることが
できます (例:’|this is a symbol|’)。
シンボルも参照して下さい。
非正確な実数の整数部または小数部のいずれかが0の場合、それを省略することが
できます。例:30., .25, -.4。
数値のリーダは、パディングの’#’を認識します。
複素数表記は直交座標形 (例:1+0.3i) でも極座標形 (例:3.0@1.57) でも
認識されます。
非正確な実数は、正の無限大、負の無限大、非数(NaN)を含み、
それらはそれぞれ+inf.0、-inf.0、および+nan.0と
表記されます。(-nan.0も非数(NaN)として読まれます)。
Gaucheはまた、SRFI-169 (数値中のアンダースコア)構文をサポートしています。
読みやすくするために、数値中に_を挿入することができます
(例: #b1100_1010_1111_1110)。
ただし、各アンダースコアは数字に囲まれていなければなりません。
1_2_3はokですが、_123、123_、12__3は
有効な数値リテラルではありません。
Gaucheはまた、Common Lisp風の基数を明示した数値リテラルも認識します。
例えば3進数の120は#3r120と書けます(10進数で15)。2進数から36進数まで
認識されます。10進数より上ではa-zA-Zのアルファベットを使えます。
複素数の極座標記法において、Gaucheではサフィックスpiをつけることにより
偏角をπの係数で表すことができます。Schemeの構文では偏角はラジアンですが、
πは浮動小数点数では近似値でしか扱えないので、偏角ゼロ以外で切りの良い数値を
表現することができません。
gosh> 2@3.141592653589793 -2.0+2.4492935982947064e-16i
piサフィックスを使うと切りの良い数値が書けます。
gosh> 2@1pi -2.0 gosh> 2@0.5pi 0.0+2.0i gosh> 2@-0.5pi 0.0-2.0i
いくつかのリテラル中では、文字をその文字コードの16進数表記で記入できます。 具体的には、文字、文字集合、文字列、シンボル、正規表現リテラルです。
R7RSは文字列および縦棒で囲まれたシンボル中では\xNNNN;、文字単独では
#\xNNNNというエスケープ構文を採用しました。16進数の桁数は可変で、
文字コードはUnicodeコードポイントです。
Gaucheは歴史的に2種類のエスケープを使ってきました。
\uと\xです。
uはUnicodeコードポイントに、xは内部エンコーディングによる
文字コードに使っていました。また、文字リテラル以外では
16進数の桁数は固定で、したがってR7RSのような終端文字(;)を必要としませんでした。
0.9.4からは、\xエスケープはそれが正しいR7RSの16進エスケープと解釈できる
限りはそう読まれます。R7RSの構文に合致しない場合は、以前のGaucheの構文とみなされます。
滅多にないことですが、R7RSとも以前のGauche構文ともみなすことができて、しかし解釈に違いが 生じるような場合というのが存在します。そのようなリテラルを含む昔のソースを 現在のGaucheで読むと、予想外の動作が起きるかもしれません。 その場合は、リーダのモードを以前との互換モードに変更できます。 詳細はリーダー字句モードを参照してください。
’#’ で始まる特殊構文がたくさん定義されています。
下の表を参照して下さい。
| • #構文: | ||
| • Hash-bangトークン: |
Next: Hash-bangトークン, Previous: 字句構造, Up: 字句構造 [Contents][Index]
以下の表はシャープ構文のリストです。
#! | [R6RS][R7RS][SRFI-22] これは、スクリプトのインタプリタ指定行(shebang)の 開始を示すか、リーダのモードに影響を与える特別なトークンとして読まれます。 下の‘hash-bang token’の節を参照してください。 |
#" | 補間された文字列を先導します。文字列の補間参照。 |
##, #$, #%, #&, #' | 未使用。 |
#( | [R7RS] リテラルベクタ表記の開始です。 |
#) | 未使用。 |
#* | ビットベクタあるいは不完全な文字列。文字列参照。 |
#+ | 未使用。 |
#, | [SRFI-10] リーダ構築子構文を開始します。 |
#-, #. | 未使用。 |
#/ | リテラルの正規表現を先導します。正規表現参照。 |
#0 … #9 | #n#, #n=: [SRFI-38] 共有サブストラクチャの定義と参照。#nR, #nr: 基数を明示した数値リテラル。 |
#: | インターンされていないシンボル。シンボル参照。 |
#; | [SRFI-62] S式コメント。続くS式をひとつ読んで捨てます。 |
#< | 読み取り不可能オブジェクトを先導します。 |
#=, #> | 未使用。 |
#? | デバッグマクロを先導します。デバッグ参照。 |
#@ | 未使用。 |
#a | 未使用。 |
#b | [R7RS] 2進数接頭辞。 |
#c | 未使用。 |
#d | [R7RS] 10進数接頭辞。 |
#e | [R7RS] 正確数接頭辞。 |
#f | [R7RS] 真理値の偽、あるいは
R7RS のユニフォームベクタを先導します。ユニフォームベクタ参照。
R7RSでは真理値の偽として#fと#falseが使えます。 |
#g, #h | 未使用。 |
#i | [R7RS] 非正確数接頭辞。 |
#j, #k, #l, #m, #n | 未使用。 |
#o | [R7RS] 8進数接頭辞。 |
#p, #q, #r | 未使用。 |
#s | [R7RS vector.@] R7RSのユニフォームベクタを先導します。ユニフォームベクタ参照。 |
#t | [R7RS] 真理値の真。R7RSでは真理値の真として#tと#trueが使えます。 |
#u | [R7RS vector.@] R7RS のユニフォームベクタを先導します。ユニフォームベクタ参照。
R7RSもバイトベクタに#u8のプリフィクスを使いますが、これは
u8ユニフォームベクタと互換です。 |
#v, #w | 未使用。 |
#x | [R7RS] 16進数接頭辞 |
#y, #z | 未使用。 |
#[ | リテラルの文字集合を先導します。文字集合参照 |
#\ | [R7RS] リテラルの文字を先導します。文字参照。 |
#], #^, #_ | 未使用。 |
#` | 文字列補間の古い構文です。新しいコードでは#"を使ってください。 |
#{ | 未使用。 |
#| | [SRFI-30] ブロックコメントを先導します。コメントは対応する ’|#’ で終ります。 |
#}, #~ | 未使用。 |
| • Hash-bangトークン: |
文字シーケンス#!は、どこでどのように現れるかによって2つの全く異なる
意味を持ちます。
ファイルが#!/もしくは#! (ハッシュ、バング、空白) から始
まっている場合、読み込みルーチンはそれをスクリプトのインタプリタ指定行
(shebang) とみなし、最初の行末までを無視します。
(実際は、ソースはファイルでなくても構いません。リーダはポートの先頭かどうかで
判断します。)
その場合以外では、#!identifierがひとつのトークンとして読ま
れ、特別な意味を持ちます。この種のトークンはデータとして読まれるのでは
なく、リーダに対して特別な指定を与えることもあります。
デフォルトでは、以下のトークンが認識されます。
#!fold-case#!no-fold-caseリーダが大文字小文字を区別するかどうかを切り替えます。
#!fold-caseに出会うとリーダは大文字小
文字を区別しないモードになり、#!no-fold-caseに出会うとその逆にな
ります。(大文字小文字の区別も参照してください。)
#!r6rsこのトークンはR6RSで導入され、プログラムがR6RSに準拠しているこ とを示します。GaucheはR6RSに準拠していませんが、今のところこのトー クンに出会っても警告を出すだけで読み込みは継続します。
#!r7rsリーダをR7RSに準拠したstrict-r7モードにします。
詳細はリーダー字句モードを参照してください。
#!gauche-legacyリーダをGauche 0.9.3およびそれ以前のものと互換なlegacyモードにします。
詳細はリーダー字句モードを参照してください。