Language Specification - 193s/marg GitHub Wiki

Language Specification

1 字句構文 - Lexical Structure

MargのソースコードはASCII printable characters(0x21-0x7F) + 空白文字(\s: TAB(0x09), Space(0x20), LF(0x0A), ...)で構成されます.
トークンの組み立てにあたり,文字は次の区分に従って区別されます.

  1. 空白文字 (Whitespace characters) : 0x20 | 0x09 | 0x0D | 0x0A
  2. 文字 (Letters) : 小文字,大文字,その他いろいろ
  3. 10進文字 (Digits) : '0' | ... | '9'
  4. 括弧 (Parentheses) : '(' | ')' | '[' | ']' | '{' | '}'
  5. 区切り文(Delimiter characters) : '`' | ''' | '"' | '.' | ';' | ','
  6. 演算子文字 (Operator characters) : ASCII printable characters (0x20-0x7E)のうち上記を除くもの全てから成ります.

1.1 識別子 - Identifiers

Syntax:
  op      ::= opchar+
  varid   ::= lower idrest
  plainid ::= upper idrest
            | varid
            | op
  id      ::= plainid
  idrest  ::= {letter | digit} ['_' op]

1.2 改行文字 - Newline Characters

Syntax:
  semi ::= ';' | nl+

1.3 リテラル - Literals

整数,文字,ブール値,文字列用のリテラルがあります.

Syntax:
  Literal ::= ['-'] integerLiteral
            |  booleanLiteral
            |  characterLiteral
            |  stringLiteral
            |  'null'

1.3.1 整数リテラル - Integer Literals

Syntax:
  integerLiteral ::= decimalNumeral
                   | hexNumeral
  decimalNumeral ::= '0' | nonZeroDigit {digit}
  hexNumeral     ::= '0' 'x' hexDigit+
  hexDigit       ::= digit | 'a' | ... | 'f'
  digit          ::= '0' | nonZeroDigit
  nonZeroDigit   ::= '1' | ... | '9'

1.3.2 真偽値リテラル - Boolean Literals

Syntax:
  booleanLiteral ::= 'o' | 'x'

oは真,xは偽を表します.

1.3.3 文字リテラル - Character Literals

Syntax:
  characterLiteral ::= '\'' printableChar '\''
                     | '\'' charEscapeSeq '\''

文字リテラルは引用符で囲まれた単一文字です.

1.3.4 文字列リテラル - String Literals

Syntax:
  stringLiteral ::= '\"' {stringElement} '\"'
  stringElement ::= printableCharNoDoubleQuote | charEscapeSeq

文字列リテラルはダブルクォートで囲まれた文字の並びです.文字は,印字可能であるか,エスケープシーケンスで記述されているかのいずれかです.

1.3.5 エスケープシーケンス - Escape Sequences

次のエスエープシーケンスは,文字あるいは文字列リテラル中で認識されます.
\b : バックスペース BS
\t : 水平タブ HT
\n : ラインフィード LF
\f : フォームフィード FF
\r : キャリッジリターン CR
" : ダブルクォート "
' : シングルクォート '
\\ : バックスラッシュ \

文字あるいは文字列リテラル中のバックスラッシュ文字が,有効なエスケープシーケンスを成さない場合,エラーが発生します.

1.4 空白文字とコメント - Whitespace and Comments

トークンは空白文字あるいはコメントで分割できます.コメントには2つの形があります:

  1. 一行コメント - Single-line Comment
    #から行末までがコメントとして扱われます.
  2. 複数行コメント - Multi-line Comment
    #--から--#までがコメントとして扱われます.

2 識別子,名前,スコープ - Identifiers, Name, and Scopes

そのうち書きます

3 宣言と定義 - Basic Declarations and Definitions

Syntax:
  Dcl ::= 'let' ValDcl
        | 'def' FunDcl

宣言は名前を導入します.

3.1 値宣言と定義 - Value Declarations and Definitions

Syntax:
  Dcl    ::= 'let' ValDcl
  ValDcl ::= ids ':' Type
  Def    ::= 'let' PatDef
  PatDef ::= Pattern2 [':' Type] '=' Expr
  ids    ::= id {',' id}

値宣言let x : Tは,型Tの値の名前としてxを導入します.

3.2 型パラメータ - Type Parameters

Syntax:
  TypeParamClause  ::= '<' TypeParam {',' TypeParam} '>'
  TypeParam        ::= id [TypeParamClause] [':' Type]

3.3 関数宣言と定義 - Function Declarations and Definitions

Syntax:
  Dcl                 ::= 'def' FuncDcl
  FuncDcl             ::= FuncSig ':' Type
  Def                 ::= 'def' FuncDef
  FuncDef             ::= FuncSig [':' Type] '=' Expr
  FuncSig             ::= id [FuncTypeParamClause] ParamClause
  FuncTypeParamClause ::= '[' TypeParam {',' TypeParam} ']'
  ParamClause         ::= '(' [Params] ')'
  Params              ::= Param {',' Param}
  Param               ::= id [':' Type]

関数宣言はdef f psig: Tの形をとります. ここで,fは関数名,psigはそのパラメータシグニチャ,Tはその結果型です. 関数定義def f psig: T = eは,関数本体e, すなわち関数の結果を定義する式も含んでいます.

3.3 use節 - Use Clauses

Syntax:
  Use          ::= 'use' UseExpr
  UseExpr      ::= StableId '.' (id | '*')

Javaにおけるimportと同様に,パッケージあるいはクラスをインポートします.

4 式 - Expressions

Syntax:
  Expr        ::= 'if' Expr ':' {nl} Expr ['else' Expr]
                | 'for' id '<-' Expr ':' {nl} Expr
                | PrefixExpr
  PrefixExpr  ::= ['-' | '+' | '~' | '!'] SimpleExpr
  SimpleExpr  ::= BlockExpr
                | SimpleExpr1
                | 'new' id '(' Exprs ')'
  SimpleExpr1 ::= Literal
                | Path
                | '(' Expr ')'
                | SimpleExpr '.' id s
                | SimpleExpr1 ArgumentExprs
  Exprs       ::= Expr {',' Expr}
  BlockExpr   ::= '{' Block '}'
  Block       ::= {BlockStat semi} [ResultExpr]
  BlockStat   ::= Use
                | Def
                | Expr1
  ResultExpr  ::= Expr1

4.1 関数適用 - Function Applications

Syntax:
  SimpleExpr    ::= SimpleExpr1 ArgumentExprs
  ArgumentExprs ::= Expr
                  | '(' [Exprs] ')'