This object is some expansion of function, the most important thing is the bind method. Prototype help document specifically said: Prototype takes issue with only one aspect of functions: binding. The wrap method is also very important. In the class inheritance mechanism, the wrap method is used to call the parent class's method of the same name.
argumentNames
bind
bindAsEventListener
curry
defer
delay
methodize
wrap
//Extend the function's prototype through the extend method of the Object object
(, (function() {
var slice = ;
//Add args to the back of the array and return the array, internal method
function update(array, args) {
var arrayLength = , length = ;
while (length--) array[arrayLength + length] = args[length];
return array;
}
//Basically the same as the update method, but does not change the incoming parameter array, return a new array
function merge(array, args) {
array = (array, 0);
return update(array, args);
}
//Format the function parameters into an array and return
function argumentNames() {
var names = ().match(/^[\s\(]*function[^(]*\(([^)]*)\)/)[1]
.replace(/\/\/.*?[\r\n]|\/\*(?:.|[\r\n])*?\*\//g, '')
.replace(/\s+/g, '').split(',');
return == 1 && !names[0] ? [] : names;
}
//Bind the context of the execution function to the context
function bind(context) {
if ( < 2 && (arguments[0])) return this;
var __method = this, args = (arguments, 1);
return function() {
var a = merge(args, arguments);
return __method.apply(context, a);
}
}
//It is basically the same as bind, which means that the first parameter passed in must be the event object
function bindAsEventListener(context) {
var __method = this, args = (arguments, 1);
return function(event) {
var a = update([event || ], args);
return __method.apply(context, a);
}
}
//curry is the name of a mathematician. The function of this method is to pass parameters continuously. You can see if you look at the specific examples below.
function curry() {
if (!) return this;
var __method = this, args = (arguments, 0);
return function() {
var a = merge(args, arguments);
return __method.apply(this, a);
}
}
//Simple encapsulation of functions
function delay(timeout) {
var __method = this, args = (arguments, 1);
timeout = timeout * 1000
return (function() {
return __method.apply(__method, args);
}, timeout);
}
//Equivalent to delay(0.01)
function defer() {
var args = update([0.01], arguments);
return (this, args);
}
//Wrapper wraps the function to be called, implementing simple AOP function
function wrap(wrapper) {
var __method = this;
return function() {
var a = update([__method.bind(this)], arguments);
return (this, a);
}
}
//The method of incoming call displaying the current context as the first parameter
function methodize() {
if (this._methodized) return this._methodized;
var __method = this;
return this._methodized = function() {
var a = update([this], arguments);
return __method.apply(null, a);
};
}
//Return external callable function
return {
argumentNames: argumentNames,
bind: bind,
bindAsEventListener: bindAsEventListener,
curry: curry,
delay: delay,
defer: defer,
wrap: wrap,
methodize: methodize
}
})());
update, merge method: Since it is an internal method, I won't talk about it in detail. You can basically understand it by looking at the source code.
argumentNames method:
Basically, we use regular expressions to propose the parameter list in the method, delete the spaces and some special characters, and then use ',' to divide it, and finally return the parameter array. I don't understand what the use of returning == 1 in the end? I tried it, but it didn't have any effect when I went there. Let me know if I know it. Let's take a look at the example below:
var fn = function(foo, bar) { return foo + bar; };
(); //-> ['foo', 'bar']
(); //-> []
bind method:
First, judge the number of parameters passed in. At least one context parameter must be passed in. If the bind() method is called directly, the original function object will be returned. It's like not calling it.
The prototype of the bind method is as follows: bind(thisObj[, arg...]) -> Function, the first parameter can be followed by optional parameters. In the bind method, all other parameters except the first parameter are stored using the args variable: args = (arguments, 1);
var __method = this, the meaning of this sentence is to set the __method variable to the current function, and use examples to illustrate it more clearly:
var obj = {
name: 'A nice demo',
fx: function() { alert(); }
};
= 'I am such a beautiful window!';
function runFx(f) { f(); }
//The __method is equivalent to
var fx2 = (obj);
runFx(); //I am such a beautiful window!
runFx(fx2); //A nice demo
/*
Here, if we do not call f() in the runFx function, but call() directly outside, the result will be 'A nice demo'.
In fact, if we write this way: var f=;f();, we will also get ‘I am such a beautiful window!’.
Through the example above, we should be able to see the concept of the context:
(); //Context is: obj
f(); //Context is: window
It can be seen that the context is actually the object before the last '.'. If the function is called directly, the context is window
*/
Finally, an anonymous function applied to the context context is returned.
Note: var a = merge(args, arguments); the arguments and args = (arguments, 1); the arguments in this sentence are different. Take a look at the example:
var obj = {
name: 'A nice demo',
fx: function() {
alert( + '\n' + $A(arguments).joi(', '));
}
};
//The [1,2,3] here is (arguments, 1);
var fx2 = (obj, 1, 2, 3);
//The [4,5] here is merge(args, arguments); arguments inside
fx2(4, 5);
// Alerts the proper name, then "1, 2, 3, 4, 5"
bindAsEventListener method:
This method is similar to bind, the main difference is in this sentence: var a = update([event || ], args); always ensures that the first parameter of the bound function is an event object. Take a look at the example:
var obj = { name: 'A nice demo' };
function handler(e) {
var data = $A(arguments);
();
alert( + '\nOther args: ' + (', ')); }
(obj, 1, 2, 3);
//=======================
<input type="button" value="button" onclick="handle()" />
Curry method:
I personally think the example given in the help document is not good. Here is another example, and you will understand it at a glance:
var F=function(){alert((arguments,0).join(' '))};
('I').curry('am').curry('never-online').curry('')();
//I am never-online
delay and defer methods:
Basically, it is a simple package, with time units in seconds. Let's take a look at the example:
// clearing a timeout
var id = (5, 'foo');
(id);
wrap method:
Returns a function “wrapped” around the original function.
Function#wrap distills the essence of aspect-oriented programming into a single method, letting you easily build on existing functions by specifying before and after behavior, transforming the return value, or even preventing the original function from being called.
This sentence: var a = update([__method.bind(this)], arguments); means to pass the wrapped function into the wrapper function as the first parameter, and take a look at the example:
function wrapped(){
alert('wrapped');
}
//You can call the original function before wrapper or after it. Is it a bit AOP meaning?
var wrapper=(function(oldFunc,param){
//oldFunc()
alert(param);
oldFunc();
});
//wrapper,wrapped
wrapper("wrapper");
methodize method:
Takes a function and wraps it in another function that, at call time,
pushes this to the original function as the first argument.
This method first checks whether the method that will be methodized has been methodized, and checks through the internal variable this._methodized.
In the end, the methodize function returns this._methodized.
This sentence: var a = update([this], arguments); is the key, it can be seen that this is passed to this original function as the first parameter. Take a look at the example and you will understand:
// start off with a simple function that does an operation
// on the target object:
var fn = function(target, foo) { = foo; }; var object = {};
// Original method
fn(object, 'bar');
//-> 'bar'
//After calling methodize, you can see that the first parameter of the fn function target has become object
= ();
('boom!');
//-> 'boom!'
argumentNames
bind
bindAsEventListener
curry
defer
delay
methodize
wrap
Copy the codeThe code is as follows:
//Extend the function's prototype through the extend method of the Object object
(, (function() {
var slice = ;
//Add args to the back of the array and return the array, internal method
function update(array, args) {
var arrayLength = , length = ;
while (length--) array[arrayLength + length] = args[length];
return array;
}
//Basically the same as the update method, but does not change the incoming parameter array, return a new array
function merge(array, args) {
array = (array, 0);
return update(array, args);
}
//Format the function parameters into an array and return
function argumentNames() {
var names = ().match(/^[\s\(]*function[^(]*\(([^)]*)\)/)[1]
.replace(/\/\/.*?[\r\n]|\/\*(?:.|[\r\n])*?\*\//g, '')
.replace(/\s+/g, '').split(',');
return == 1 && !names[0] ? [] : names;
}
//Bind the context of the execution function to the context
function bind(context) {
if ( < 2 && (arguments[0])) return this;
var __method = this, args = (arguments, 1);
return function() {
var a = merge(args, arguments);
return __method.apply(context, a);
}
}
//It is basically the same as bind, which means that the first parameter passed in must be the event object
function bindAsEventListener(context) {
var __method = this, args = (arguments, 1);
return function(event) {
var a = update([event || ], args);
return __method.apply(context, a);
}
}
//curry is the name of a mathematician. The function of this method is to pass parameters continuously. You can see if you look at the specific examples below.
function curry() {
if (!) return this;
var __method = this, args = (arguments, 0);
return function() {
var a = merge(args, arguments);
return __method.apply(this, a);
}
}
//Simple encapsulation of functions
function delay(timeout) {
var __method = this, args = (arguments, 1);
timeout = timeout * 1000
return (function() {
return __method.apply(__method, args);
}, timeout);
}
//Equivalent to delay(0.01)
function defer() {
var args = update([0.01], arguments);
return (this, args);
}
//Wrapper wraps the function to be called, implementing simple AOP function
function wrap(wrapper) {
var __method = this;
return function() {
var a = update([__method.bind(this)], arguments);
return (this, a);
}
}
//The method of incoming call displaying the current context as the first parameter
function methodize() {
if (this._methodized) return this._methodized;
var __method = this;
return this._methodized = function() {
var a = update([this], arguments);
return __method.apply(null, a);
};
}
//Return external callable function
return {
argumentNames: argumentNames,
bind: bind,
bindAsEventListener: bindAsEventListener,
curry: curry,
delay: delay,
defer: defer,
wrap: wrap,
methodize: methodize
}
})());
update, merge method: Since it is an internal method, I won't talk about it in detail. You can basically understand it by looking at the source code.
argumentNames method:
Basically, we use regular expressions to propose the parameter list in the method, delete the spaces and some special characters, and then use ',' to divide it, and finally return the parameter array. I don't understand what the use of returning == 1 in the end? I tried it, but it didn't have any effect when I went there. Let me know if I know it. Let's take a look at the example below:
Copy the codeThe code is as follows:
var fn = function(foo, bar) { return foo + bar; };
(); //-> ['foo', 'bar']
(); //-> []
bind method:
First, judge the number of parameters passed in. At least one context parameter must be passed in. If the bind() method is called directly, the original function object will be returned. It's like not calling it.
The prototype of the bind method is as follows: bind(thisObj[, arg...]) -> Function, the first parameter can be followed by optional parameters. In the bind method, all other parameters except the first parameter are stored using the args variable: args = (arguments, 1);
var __method = this, the meaning of this sentence is to set the __method variable to the current function, and use examples to illustrate it more clearly:
Copy the codeThe code is as follows:
var obj = {
name: 'A nice demo',
fx: function() { alert(); }
};
= 'I am such a beautiful window!';
function runFx(f) { f(); }
//The __method is equivalent to
var fx2 = (obj);
runFx(); //I am such a beautiful window!
runFx(fx2); //A nice demo
/*
Here, if we do not call f() in the runFx function, but call() directly outside, the result will be 'A nice demo'.
In fact, if we write this way: var f=;f();, we will also get ‘I am such a beautiful window!’.
Through the example above, we should be able to see the concept of the context:
(); //Context is: obj
f(); //Context is: window
It can be seen that the context is actually the object before the last '.'. If the function is called directly, the context is window
*/
Finally, an anonymous function applied to the context context is returned.
Note: var a = merge(args, arguments); the arguments and args = (arguments, 1); the arguments in this sentence are different. Take a look at the example:
Copy the codeThe code is as follows:
var obj = {
name: 'A nice demo',
fx: function() {
alert( + '\n' + $A(arguments).joi(', '));
}
};
//The [1,2,3] here is (arguments, 1);
var fx2 = (obj, 1, 2, 3);
//The [4,5] here is merge(args, arguments); arguments inside
fx2(4, 5);
// Alerts the proper name, then "1, 2, 3, 4, 5"
bindAsEventListener method:
This method is similar to bind, the main difference is in this sentence: var a = update([event || ], args); always ensures that the first parameter of the bound function is an event object. Take a look at the example:
Copy the codeThe code is as follows:
var obj = { name: 'A nice demo' };
function handler(e) {
var data = $A(arguments);
();
alert( + '\nOther args: ' + (', ')); }
(obj, 1, 2, 3);
//=======================
<input type="button" value="button" onclick="handle()" />
Curry method:
I personally think the example given in the help document is not good. Here is another example, and you will understand it at a glance:
Copy the codeThe code is as follows:
var F=function(){alert((arguments,0).join(' '))};
('I').curry('am').curry('never-online').curry('')();
//I am never-online
delay and defer methods:
Basically, it is a simple package, with time units in seconds. Let's take a look at the example:
Copy the codeThe code is as follows:
// clearing a timeout
var id = (5, 'foo');
(id);
wrap method:
Returns a function “wrapped” around the original function.
Function#wrap distills the essence of aspect-oriented programming into a single method, letting you easily build on existing functions by specifying before and after behavior, transforming the return value, or even preventing the original function from being called.
This sentence: var a = update([__method.bind(this)], arguments); means to pass the wrapped function into the wrapper function as the first parameter, and take a look at the example:
Copy the codeThe code is as follows:
function wrapped(){
alert('wrapped');
}
//You can call the original function before wrapper or after it. Is it a bit AOP meaning?
var wrapper=(function(oldFunc,param){
//oldFunc()
alert(param);
oldFunc();
});
//wrapper,wrapped
wrapper("wrapper");
methodize method:
Takes a function and wraps it in another function that, at call time,
pushes this to the original function as the first argument.
This method first checks whether the method that will be methodized has been methodized, and checks through the internal variable this._methodized.
In the end, the methodize function returns this._methodized.
This sentence: var a = update([this], arguments); is the key, it can be seen that this is passed to this original function as the first parameter. Take a look at the example and you will understand:
Copy the codeThe code is as follows:
// start off with a simple function that does an operation
// on the target object:
var fn = function(target, foo) { = foo; }; var object = {};
// Original method
fn(object, 'bar');
//-> 'bar'
//After calling methodize, you can see that the first parameter of the fn function target has become object
= ();
('boom!');
//-> 'boom!'