質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
Lua

Luaは、汎用のスクリプト言語の一つで、 移植性が高く、高速な実行速度などの特徴を持ち 手続き型・オブジェクト指向言語としても利用可能で 関数型言語、データ駆動型の要素も併せ持っている言語です。

Q&A

解決済

1回答

2735閲覧

Luaのカリー化関数について

keisukeoo

総合スコア146

Lua

Luaは、汎用のスクリプト言語の一つで、 移植性が高く、高速な実行速度などの特徴を持ち 手続き型・オブジェクト指向言語としても利用可能で 関数型言語、データ駆動型の要素も併せ持っている言語です。

0グッド

0クリップ

投稿2014/09/09 00:26

Luaの関数型言語としての特徴として、カリー化関数をサポート
していることがあげられますが、
この簡単なコード例を示して頂けませんか?
Lua言語で理解したいです。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

Lua が関数型というのには、ちょっと引っかかりますが、とりあえず説明してみたいと思います。

カリー化というのは「 2 つ以上の引数を持つ関数を 1 つの引数の関数の組み合わせになおす」ことを言います。

次のような関数をカリー化してみます。

lang

1function plus(a, b) 2 return a + b 3end 4 5print(plus(2, 3)) -- 5

カリー化は戻り値として関数を返すことによって実現します。

lang

1function cplus(a, b) 2 return function(b) return a + b end 3end 4 5print(cplus(2)(3)) -- 5

plus(2, 3) と書いていたものが cplus(2)(3) と書けるようになりました。これがカリー化です。

このカリー化した関数を使ってみます。

まず、テーブルに関数を適用して新しいテーブルを返す関数mapを作成します。
関数型の機能を取り入れた言語では通常デフォルトであるのですが、 Lua の場合は自分で作る必要があります。

lang

1function map(func, array) 2 local new_array = {} 3 for i,v in ipairs(array) do 4 new_array[i] = func(v) 5 end 6 return new_array 7end 8 9src = {1,2,3} 10dest = map(function(x) return 2 + x end, src) 11print(table.concat(dest,", ")) -- 3, 4, 5

map に渡す関数をカリー化した関数を変えます。

lang

1dest = map(cplus(2), src) 2print(table.concat(dest,", ")) -- 3, 4, 5

map は引数を一つだけとる関数のみを受け付けるのですが、関数がカリー化してあることによって、そこに関数を渡せるようになっています。
このように関数がカリー化してあると引数として渡す際に柔軟に対応できるようになります。

関数型では高階関数といって関数を引数に渡すことがよくあります。その辺についても補足しておきます。

まず、関数型プログラミングのポイントに以下の点があります。

関数は数学的な意味での関数 → 副作用を伴わない
→ 一度作成した変数は変更しない(参照透過性)

変数を変更しないというのは大きな制約で、関数型では ループ ができません。
カウンターやイテレーターといったものが使えないためです。

ループを一番よく使う場面というのはコレクション(Lua ではテーブル)の要素を処理していく場合だと思います。
そのため、関数型では map のような関数で関数を適用してデータ処理を行うという手法がよくとられています。

ちなみにコレクションの処理以外のループはどうするかというと「再帰」を使います。
再帰はループに比べるとスタックを積むのでメモリーを大量に消費してしまって不利です。そこで関数型の言語には「関数末尾の再帰最適化」の機能が求められます。
この機能は Lua にもあります。

投稿2014/09/09 17:44

yohshiy

総合スコア863

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

keisukeoo

2014/09/10 05:15

とても親切な回答ありがとうございました!補足で色々説明してくださったおかげでイメージがつきました!ありがとうございました!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問