The small demo below illustrates my problem:
// 1 - Define a global reference to classA
(function() {
window.classA = new ClassA();
})();
// 2 - ClassA object definition
function ClassA() {
this.test1 = function() {
document.write('test1');
};
}
// 3 - ClassA inherits Array and has a test function
ClassA.prototype = new Array;
ClassA.prototype.test2 = function() {
document.write(this[0]);
}
// 4 - Test our ClassA
var c = new ClassA();
c.test1();
c.push('test2');
c.test2();
// 5 - Test our global ClassA
classA.test1();
classA.push('test2'); // doesn't work
classA.test2(); // doesn't work
Try it here: http://jsfiddle.net/SPSW4/
What is the proper way to define a global variable classA (ClassA instance)?
-
you mean global as in static? did you consider reordering of your function calls?Caspar Kleijne– Caspar Kleijne2011年09月03日 14:36:28 +00:00Commented Sep 3, 2011 at 14:36
-
global variable (an instance of ClassA)Yvo– Yvo2011年09月03日 14:40:20 +00:00Commented Sep 3, 2011 at 14:40
-
there are no classes in JavaScript and naming a function class makes no sense. This makes it very confusing to read. Please reconsider your naming convention ;)Caspar Kleijne– Caspar Kleijne2011年09月03日 14:43:54 +00:00Commented Sep 3, 2011 at 14:43
-
simply an example, please pay no attention to the names :)Yvo– Yvo2011年09月03日 14:49:06 +00:00Commented Sep 3, 2011 at 14:49
6 Answers 6
The correct approach would be to create the pseudo-sub-classed Array constructor within an immediately invoked function expression and then expose the result to an explicit global object.
(function( global ) {
// Declare the ArrayLike constructor
function ArrayLike() {
var args = [].slice.call( arguments ),
length = args.length, i = 0;
this.length = length;
for ( ; i < length; i++ ) {
this[ i ] = args[ i ];
}
return this;
}
// Define ArrayLike's prototype by creating a new Array instance
ArrayLike.prototype = new Array();
// Define your own proto method
ArrayLike.prototype.firstChar = function() {
var ret = [],
length = this.length, i = 0;
for ( ; i < length; i++ ) {
ret[ i ] = this[ i ][ 0 ];
}
return ret;
};
// Expose the ArrayLike constructor.
global.ArrayLike = ArrayLike;
})( this );
var a = new ArrayLike( "alpha", "beta", "gamma" );
console.log( a.push("delta") ) // 4
console.log( a ); // ["alpha", "beta", "gamma", "delta"]
console.log( a.firstChar() ); // ["a", "b", "g", "d"]
See it live: http://jsfiddle.net/rwaldron/gLdkb/
Comments
Your code appears to be binding the global classA variable before ClassA is fully defined. I believe you will have more luck if you do it like:
// 1 - define ClassA
window.ClassA = function() {
this.test1 = function() {
document.write('test1');
};
};
ClassA.prototype = new Array;
ClassA.prototype.test2 = function() {
document.write(this[0]);
}
// 2 - Define a global reference to classA
window.classA = new ClassA();
// 3 - Test our ClassA
var c = new ClassA();
c.test1();
c.push('test2');
c.test2();
// 4 - Test our global ClassA
classA.test1();
classA.push('test2'); // doesn't work
classA.test2(); // doesn't work
Here's an example: http://jsfiddle.net/SPSW4/2/
7 Comments
window.classA = new ClassA(); just needs to occur after you are done configuring ClassA.new keyword. Since those methods aren't attached at the time of ... = new ClassA() the object doesn't see them.ClassA.prototype = Array.prototype then won't adding a new method to ClassA also cause that new method to appear in Array? Perhaps using new Array avoids that issue?swap
// 2 - ClassA object definition
function ClassA() {
this.test1 = function() {
document.write('test1');
};
}
// 1 - Define a global reference to classA
(function() {
window.classA = new ClassA();
})();
declaration before calling functions in JavaScript, it is a scripting language.
1 Comment
Try this:
// 2 - ClassA object definition
function ClassA() {
this.test1 = function() {
document.write('test1');
};
}
// 3 - ClassA inherits Array and has a test function
ClassA.prototype = new Array;
ClassA.prototype.test2 = function() {
document.write(this[0]);
}
// 4 - Test our ClassA
var c = new ClassA();
c.test1();
c.push('test2');
c.test2();
// 1 - Define a global reference to classA
window.classA = new ClassA();
// 5 - Test our global ClassA
classA.test1();
classA.push('test2');
classA.test2();
Actually there were two problems: 1. Creating object before declaring class 2. Creating object before extending class
3 Comments
new ClassA() until after ClassA is fully defined. A reasonable way to do this is to move the window.classA = new ClassA(); part so that it is at the very end of the file that defines ClassA.if (typeof(classA) === 'undefined') window.classA = new ClassA();. Ugly but will work.Define your class
ClassA = function()
{
this.test1 = function()
{
document.write('test1');
};
};
Then apply array prototype
ClassA.prototype = Array.prototype;
Then you can extend your class
ClassA.prototype.test2 = function()
{
document.write(this[0]);
};
About the "global reference" part. In the first part of your code your are not making a reference, you are instancing a class which has not been defined yet at that point. There is no need to do that also. What is your point with that part?
Comments
Move the class definition before the call.
Note: The only thing that really needs to come first is the prototyping, since your code first assigns the class, but never sees the effect of the prototyping, which occurs later. Your class assignment should come after the prototypes.
You're missing a
;after thetest2()definition.
// Class Definition
function ClassA() {
this.test1 = function() { document.write('foo'); };
}
ClassA.prototype = new Array();
ClassA.prototype.test2 = function() { document.write(this[0]); };
// Init
(function() {
window.classA = new ClassA();
})();
// Method Calls
var c = new ClassA();
c.test1();
c.push('bar');
c.test2();
classA.test1();
classA.push('bar');
classA.test2();
Comments
Explore related questions
See similar questions with these tags.