Erg言語を触ってみた
ClaudeCodeに新し目の関数型言語について聞いてみたら紹介されたので、試しにやってみたという記事です。
結論から言うと、まだ開発中ということもあり、マニュアルなどのメンテもイマイチだったりして本格的に利用するのは厳しそうという感じでした。
Ergについて
Ergについては、このあたりで説明されている内容を読むと雰囲気がわかります。
- 公式 : https://erg-lang.org/
- GitHub : https://github.com/erg-lang/erg
インストール
インストール環境は MacOS 15.6.1 (Sequoia)
で行っています。
基本的には以下の手順に沿ってインストールを行います。
ErgはRustを利用して実装されており、インストールするためにRustのビルド&パッケージマネージャであるcargo
が必要になります。
cargo
はRust関連パッケージのインストールで同時にインストールされるので、以下のrustup-init
をインストールして下さい。
brew install rustup-init
rustup-init
以下のコマンドでErg
をインストールします。
cargo install erg
失敗する場合は、cargo
が古い可能性があるので以下のコマンドを実行してバージョンアップして下さい。
rustup update
手元の環境では以下のバージョンでインストールに成功しました。
cargo --version # cargo 1.89.0 (c24e10642 2025-06-23)
開発環境
VSCode
VSCodeのプラグインが公式からリリースされていますが、デバッグ機能等もまだ無いので、ターミナルから実行する方式で問題ないと思います。
vim
以下のような設定を入れておくと、ショートカットで実行ができるので楽です。
nnoremap [Exec] <Nop>
nmap <C-t> [Exec]
map <silent> [Exec]p :!erg run %<CR>
" Python出力
map <silent> [Exec]cp :!erg transpile %<CR>
" Pythonバイトコード(pyc)出力
map <silent> [Exec]cb :!erg compile %<CR>
" 型チェック
map <silent> [Exec]tc :!erg typecheck %<CR>
" フルチェック(ownership check, effect check, ...)
map <silent> [Exec]ta :!erg check %<CR>
" Linter (文法などのチェック)
map <silent> [Exec]f :!erg lint %<CR>
その他インデントなどの設定
Erg用のプラグインが今のところ存在しないようなので
ClaudeCodeで自動生成したところ、割といい感じのものを作ってくれました。
必要に応じて .vimrc
ファイルなどに追記して下さい。
詳細
autocmd BufNewFile,BufRead *.er,*.erg set filetype=python
autocmd FileType erg setlocal
\ tabstop=4
\ shiftwidth=4
\ expandtab
\ autoindent
\ commentstring=#\ %s
" シンタックスの設定
if !exists("b:erg_syntax")
let b:erg_syntax = 1
" Keywords
syn keyword ergKeyword if else elif match case when do
syn keyword ergKeyword import from as export
syn keyword ergKeyword let var const mut
syn keyword ergKeyword class trait impl enum union
syn keyword ergKeyword fn proc macro
syn keyword ergKeyword return yield break continue
syn keyword ergKeyword try catch finally raise
syn keyword ergKeyword and or not in is
syn keyword ergKeyword for while loop
syn keyword ergKeyword true false None
" Types
syn keyword ergType Int Float Str Bool
syn keyword ergType Nat Ratio Complex
syn keyword ergType Array Dict Set Tuple
syn keyword ergType Option Result
syn keyword ergType Self self
" Operators
syn match ergOperator "+"
syn match ergOperator "-"
syn match ergOperator "\*"
syn match ergOperator "/"
syn match ergOperator "%"
syn match ergOperator "="
syn match ergOperator "=="
syn match ergOperator "!="
syn match ergOperator "<"
syn match ergOperator ">"
syn match ergOperator "<="
syn match ergOperator ">="
syn match ergOperator "->"
syn match ergOperator "=>"
syn match ergOperator "|"
syn match ergOperator "&"
syn match ergOperator "!"
syn match ergOperator "?"
" Numbers
syn match ergNumber "\<\d\+\>"
syn match ergNumber "\<\d\+\.\d\+\>"
syn match ergNumber "\<0x[0-9a-fA-F]\+\>"
syn match ergNumber "\<0b[01]\+\>"
syn match ergNumber "\<0o[0-7]\+\>"
" Strings
syn region ergString start='"' skip='\\"' end='"'
syn region ergString start="'" skip="\\'" end="'"
syn region ergString start='"""' end='"""'
" Comments
syn match ergComment "#.*$"
syn region ergComment start="#\*" end="\*#"
" Functions
syn match ergFunction "\<[a-zA-Z_][a-zA-Z0-9_]*\>\s*("he=e-1
" Variables (mutable)
syn match ergMutable "\<[a-zA-Z_][a-zA-Z0-9_]*!"
" Decorators/Attributes
syn match ergDecorator "@[a-zA-Z_][a-zA-Z0-9_]*"
" Highlighting
hi def link ergKeyword Keyword
hi def link ergType Type
hi def link ergOperator Operator
hi def link ergNumber Number
hi def link ergString String
hi def link ergComment Comment
hi def link ergFunction Function
hi def link ergMutable Identifier
hi def link ergDecorator PreProc
endif
" Indentの設定
if !exists("b:erg_indent")
let b:erg_indent = 1
setlocal indentexpr=GetErgIndent()
setlocal indentkeys=0{,0},0),0],:,!^F,o,O,e
setlocal autoindent
setlocal nosmartindent
function! GetErgIndent()
let line = getline(v:lnum)
let prevline = getline(v:lnum - 1)
" 基本的なインデント
if prevline =~ ':\s*$'
return indent(v:lnum - 1) + &shiftwidth
endif
" ブロック終了
if line =~ '^\s*}'
return indent(v:lnum - 1) - &shiftwidth
endif
" デフォルト
return indent(v:lnum - 1)
endfunction
endif
ファイル拡張子
*.er
もしくは *.erg
を利用するとのことです。
コマンド
詳細はerg -h
を参照して下さい。
ファイルの実行
# 以下のいずれかで実行する
erg sample.er
erg run sample.er
erg exec sample.er
Pythonコードに変換
erg transpile sample.er
バイトコードに変換(*.pyc)
erg compile sample.er
型チェック
# 以下のいずれかで実行する
erg tc sample.er
erg typecheck sample.er
文法
基本的には以下のマニュアルを読めば良さそうな感じです。
動作確認
以下のGitHub上に記載されているコードを貼り付けて実行すると...
l = [1, 2, 3]
assert l in [Nat; 3] # type checking
Error[#2604]: File sample.er, line 54, <module>
54 | assert l in [Nat; 3] # type checking
: -
: |- expected: {Nat}..Obj
: `- but found: {[1, 2, 3]}
TypeError: the type of `contains`::rhs (the 2nd argument) is mismatched
shell returned 1
ということでエラーになりました...
ちなみに、利用しているErgのバージョンは Erg 0.6.53
になります。
最後に
Ergは絶賛開発中ということで、おそらく古いバージョンでは動いていたのだと思いますが、マニュアルなどのメンテナンスが追いついていないので、公式で紹介しているコードでも動かないものがあるようです。
こちらのマニュアルで紹介されているコードに関しても、動いたり動かなかったりなので、今現在は、プログラミングを本格的に行っていくのは難しいのかなと思いました。
文法的には結構面白そうだったので、今後に期待したいです。