星にゃーんのブログ

ほとんど無害。

Haskell

継続モナドで立ち向かうローンパターンとEither地獄

Haskellでファイルなどのリソースの解放を保証するテクニックとして、ローンパターン(Loan Pattern)がある。withFile :: FilePath -> IOMode -> (Handle -> IO r) -> IO rなどがその例だ。 ローンパターンによる関数を複数使ったプログラムは、無名関数の…

Haskellのsomeを正格評価したら無限ループする話

パーサコンビネータなんかでよく使う、 some と many という関数があります。それぞれ引数を1回以上/0回以上実行して結果のリストを返す関数で、これの単純な定義は some v = (:) <$> v <*> many v many v = some v <|> pure [] となります。 some は v : …

地味なバグと誰かの囁き声

最近(ここ数年?)malgoというプログラミング言語を作ってる。 今日、地味なバグを見つけた。厳密にはバグじゃない気もするんだけど、ユーザーの直感に反するような挙動をする。 例えば、Eitherを定義するとする。 data Either a b = Left a | Right b; す…

自作プログラミング言語Malgoがかなりそれっぽくなってきた

プログラミング言語Malgo 2017ごろから、自作のプログラミング言語Malgoとそのコンパイラを作っている。 2018年の2月に、このことをブログに書いた。 あれから三年経ち、色々とできることが増えた…かというと、そうでもない。 しかし、言語設計はかなり変わ…

RebindableSyntaxとGHC.Genericsを使って'genericなif'を作る

CoqのGallinaでは2つのコンストラクタC1, C2のある型Tの式vについて、 if v then t1 else t2 が match v with | C1 ... => t1 | C2 ... => t2 end にdesugarされる。 なんだかよくわからないけどかっこいい!!!Haskellでもこれやりたい!!! やりました。…

プログラミング言語をつくっている

去年の夏頃からプログラミング言語を作っています。 こんな感じのソースコードから let extern print_int : Int -> Unit = "print_int" extern newline : Unit -> Unit = "newline" fun fib(n : Int) : Int = if n <= 1 then 1 else fib(n - 1) + fib(n - 2)…

Hakyllでブログ作った

こうののブログ - Home stackにはHakyll用のテンプレートもあるので、ブログ制作そのものは簡単にできる。 Github Pagesの仕様にあわせるため若干のハックが必要だった。 具体的には、記事作成そのものはblogブランチで行い、_site/以下をmasterブランチにコ…

GHCでFizzBuzz

GHCでFizzBuzzを書いた。 gen_nats(Max, Ns) :- true | gen_integers(1, Max, Ns). gen_integers(N, Max, Is) :- N =< Max | Is = [N | Is1], N1 := N + 1, gen_integers(N1, Max, Is1). gen_integers(N, Max, Is) :- N > Max | Is = []. map([], Fs) :- tru…