What is it, naokirin?

ラムダ式の色々

今日、C++0xで実装されるラムダ式が「旧型のロボット」みたいなイメージという話をしたので、どうせなら他の言語のラムダ式 ( 匿名関数、無名関数 ) と比較してみようと何となく思ったり。

ちなみにラムダ式 ( 無名関数 ) の部分のみ抜き出して書いています。(普通は変数などに束縛しないと意味がないです。)
間違っている可能性もあるのであまり参考になさらずに。

動作は引数numを一つ取って、num * num となる結果を返すようなものです。(ただし、型を明示しなければならない場合は引数はint型とします。)

C++0x

[]( int num ) -> int { return num * num; }
[]( int num ) { return num * num; } // 上と同じ。

C++0xでは型を明示しなければなりませんが、関数内が return 式のみの場合は必要ないようです。

Java

残念ながら実装は Java SE 8 まで見送り?みたいですね。
こんな感じの実装になる?みたいなことはWebにあったりしますが…

C#

( int num ) => num * num;
( int num ) => { return num * num; } // 上と同じ

明らかに型がわかるような場合には型を省略して書けるらしい。
デリゲートとする場合には

//   Func<引数の型, ... , 戻り値の型>でデリゲート
Func<int, int> f = ( num ) => { return num * num; }

Ruby

->( num ){ num * num }
lambda { |num| num * num }

Rubyには二通りのラムダ式の書き方があるようです。注意としては二つそれぞれ使い方が異なり

->( num ){ num * num }.call( 2 )  #=> 4
lambda { |num| num * num }.( 2 )  #=> 4

のような形で使います。変数に束縛した場合でも同じです。

Python

lambda num: num * num

初めて見ました。

JavaScript

function ( num ) { return num * num; }

良く考えてみると私が初めてラムダ式を見たのは、JavaScriptのコードかもしれません。

Scala

( num :Int ) => num * num

私は一度もScalaに触ったことないので、Scalaで一番最初に知った文法はラムダ式になりました(笑)

OCaml, F#

fun num -> num * num

基本的な文法が同じなので、ラムダ式あたりは全く同じで良いようですね。

Lisp

(lambda ( num ) (* num num)))

かなりあってるか自信ないwww

Haskell

\num -> num * num

Erlang

fun (Num) -> Num * Num end


他の言語でも実装されていると思いますがこれだけあれば、大体見比べるには十分かと。有名どころだとラムダ式の実装がよくわからないのはJavaくらいでしょうか。SE 8まで先延ばしになったようですね。

基本的には

キーワード ( 引数 ) -> 処理

の形が多くて、-> やキーワードを省略しているものが多いようです。

C++0xラムダ式の違和感の原因としては、"[]"のせいかなと。これが堅苦しい感じ、不格好な感じを演出しているみたいです。
こうやって見比べてみると、他の言語の場合とあまり差異はないようですね。