Reputation: 1
In javascript, why this? And for the hell of me, I can't find anything explaining it
Say
var ATest = function(atom, electron)
{
this.atom = atom;
this.electron = electron;
}
ATest.prototype.atom = 'emptyAtomA';
ATest.prototype.electron = 1;
I come from C# and this prototype thing is like default constructor values for javascript objects
so, i try this in Chrome console:
var ATestVariable = new ATest();
ATestVariable.atom
//Result->undefined
ATestVariable.electron
//Result->undefined
And this is strange for me, so I try in the global context (don't know, maybe using this has produced some weird assignemnt...)
this.atom
//Result->undefined
this.electron
//Result->undefined
window.atom
//Result->undefined
Nothing here too.
Now, if I try
var BTest = function(Atom, Electron)
{
atomB = Atom;
electronB = Electron;
}
BTest.prototype.atom = 'emptyAtomB';
BTest.prototype.electron = 12;
And then I do
var BTestVariable = new BTest();
BTestVariable.atom
//Result->"emptyAtomB"
BTestVariable.electron
//Result -> 12
This is what I get and what I would expect in both cases.
What is happening?
Upvotes: 1
Views: 44
Reputation: 37755
You're not passing any parameter to constructor when you're calling new ATest
, so the value assigned to this.atom
and this.electron
turns out to be undefined
var ATest = function(atom, electron)
{
this.atom = atom;
this.electron = electron;
}
// when values not passed to constructor
var ATestVariable = new ATest();
console.log(ATestVariable)
// when values passed to constructor
var BTestVariable = new ATest(1, 'some value');
console.log(BTestVariable)
Not let's talk about values added to prototype
, the values are are ATest
internal prototype so you need to get access values using that
var ATest = function(atom, electron)
{
this.atom = atom;
this.electron = electron;
}
ATest.prototype.atom = 'emptyAtomA';
ATest.prototype.electron = 1;
let a = new ATest()
console.log(Object.getPrototypeOf(a).atom)
console.log(a.__proto__.atom)
Upvotes: 0
Reputation: 370689
When you do
var ATest = function(atom, electron)
{
this.atom = atom;
this.electron = electron;
}
ATest.prototype.atom = 'emptyAtomA';
ATest.prototype.electron = 1;
The first and second parameters passed to the constructor will be assigned to properties of the instance (this
) no matter what. If you do not pass any parameters, then the values of the standalone variables atom
and electron
will be undefined
, so the instance ends up having own properties atom
and electron
whose values are undefined
.
The instance still has an internal prototype object, and that internal prototype has property values emptyAtomB
and 12
, but because the instance has own properties with the same name, they overshadow the properties on the internal prototype.
var ATest = function(atom, electron)
{
this.atom = atom;
this.electron = electron;
}
ATest.prototype.atom = 'emptyAtomA';
ATest.prototype.electron = 1;
var ATestVariable = new ATest();
console.log(ATestVariable.atom);
console.log(Object.getPrototypeOf(ATestVariable).atom);
It sounds like you may be wanting to check to see if the arguments are defined first:
var ATest = function(atom, electron)
{
if (atom !== undefined) {
this.atom = atom;
}
if (electron !== undefined) {
this.electron = electron;
}
}
When you do
var BTest = function(Atom, Electron)
{
atomB = Atom;
electronB = Electron;
}
you're assigning the parameters to global variables atomB
and electronB
. This is not desirable, and will throw an error in strict mode.
Of course, it would be best to simply always pass all expected arguments to the constructor every time, if that's what your script expects:
var ATest = function(...args)
{
if (args.length !== 2) {
throw new Error('Two arguments required: atom and electron');
}
const [atom, electron] = args;
this.atom = atom;
this.electron = electron;
}
Upvotes: 1