function.nameについて
全てのfunctionはFunction.prototype.nameというプロパティを持ちます。
funciton.nameとはその名の通りFunctionの名前を取得することができます。
実行環境はnode v6.2.0です。
var func1 = function hoge() {};
console.log(func1); // [Function: hoge]
console.log(func1.name); // "hoge"
var func2 = function() {};
console.log(func2); // [Function]
console.log(func2.name); // ""
function fuga() {}
console.log(fuga); // [Function: fuga]
console.log(fuga.name); // "fuga"
大きいプロジェクトになればなるほど、このfunctionはなんだっけかな。。ということが稀に発生します。名前をつけておくととても効率的にデバッグが行えるかと思います。
最近のv8のバージョンではbindした際には"bound xxx"というnameを保持するようになりましたが、以前のバージョンや実行環境によっては失われてしまうケースもあります。
var func = function hoge() {};
console.log(func.bind(null)); // [Function: bound hoge]
console.log(func.bind(null)); // [Function] (node v0.12.12)
またfunction.nameは書き込み不可なプロパティです。
var func = function hoge() {};
func.name = 'fuga';
console.log(func); // [Function: hoge]
console.log(func.name); // "hoge"
new Functionではnameを変更することができません。
var func = new Function('val', '{ return val; }');
console.log(func); // [Function: anonymous]
console.log(func); // [Function] (node v0.12.12)
Funciton.nameを変更する
実際には新しい名前付きの新しいFunctionを生成します。
新しい関数を生成しますので使用する際には十分気をつけてください。
// Function
var name = 'hoge';
var str = '{ return function ' + name + '(val) { return val;}; }'
var func = new Function(str)();
console.log(func); // [Function: hoge]
既存の関数の名前を変更したい場合は、
function rename(func, name) {
var str = func.toString().replace(/^function(.*?)\(/, 'return function ' + name + '(');
return new Function(str)();
}
var func1 = function hoge(val) { return val; };
var func2 = rename(func1, 'fuga');
console.log(func1); // [Function: hoge]
console.log(func2); // [Function: fuga]
新しい名前付きの関数を作成する
このようにすることで新しい名前付きの関数を作成できます。
function makeFunc(name, args, fstr) {
var arr = [name, args, fstr];
var str = 'return function %s(%s) %s;';
str = str.replace(/%s/g, function() {
return arr.shift();
});
return new Function(str)();
}
var name = 'test';
var args = ['a', 'b'];
var fstr = '{ return a + b; }';
var func = makeFunc(name, args, fstr);
console.log(func(1, 2)); // 3
もう少しだけ汎用的にしたものをGitHubにあげてありますので、興味がある方は見てみてください。
https://github.com/suguru03/make-function