issue with eval in a prototyped function

G

graphicsxp

Hi,

Consider the following code :

<script type="text/javascript">

function Test() {
this.init();
}
var t = Test.prototype;

t.init = function() {
this.name = 'Test';
eval(this.name + '=this');
}

function create() {

var t = new Test();
}
</script>

<input type="button" onclick="create()" />


The first time the button is clicked, it creates an instance of Test
and the init function is called. However if the button is clicked
again, an exception is raised : 'Object doesn't support this action'.

If I comment the line eval(this.name + '=this'); , then there is no
more error.

I'm trying to understand what is the issue there. Is there some code
I could run before I re-create the object in order to destroy the
previous instance ?

Thanks
 
R

Richard Cornford

Consider the following code :

<script type="text/javascript">

function Test() {
this.init();
}
var t = Test.prototype;

t.init = function() {
this.name = 'Test';
eval(this.name + '=this');
}

function create() {

var t = new Test();
}
</script>

<input type="button" onclick="create()" />

The first time the button is clicked, it creates an instance
of Test and the init function is called. However if the button
is clicked again, an exception is raised : 'Object doesn't
support this action'.

As expected, given that the - eval(this.name + '=this'); - line
assigns a reference to the object being constructed to a property of
the global object that has the name "Test", and up until that point
had been a reference to the function that is being used as the
constructor.
If I comment the line eval(this.name + '=this'); , then
there is no more error.

Yes, if you don't replace the constructor while constructing the
constructor will still be there next time you attempt to use it.
I'm trying to understand what is the issue there.

The code that - eval - is executing is - Test=this -, which is an
assignment to an unqualified Identifier. The Identifier is resolved by
working up the function's scope chain until an object on the scope
chain has a property named "Test" and assigning a value to that
property. The function name "Test" exists as a property of the global
object named "Test" and assigned a value that is a reference to a
function object. The global object is the last object on all
javascript function's scope chains.
Is there some code I could run before I re-create the object
in order to destroy the previous instance ?

No. But whatever it is you are trying to achieved here the odds are
very good that it can be done, even if mind reading abilities don't
run to knowing what it is without your saying.

Richard.
 
L

Lasse Reichstein Nielsen

Consider the following code :

<script type="text/javascript">

function Test() {
this.init();
}
var t = Test.prototype;

t.init = function() {
this.name = 'Test';
eval(this.name + '=this');

This statement is equivalent to the statement
Test = this;
So, you overwrite the Test function.
Don't use eval. It makes error-finding much easier.
The first time the button is clicked, it creates an instance of Test
and the init function is called. However if the button is clicked
again, an exception is raised : 'Object doesn't support this action'.

As expected. The Test variable no longer holds a function, but just
an object.
If I comment the line eval(this.name + '=this'); , then there is no
more error.
Yes.

I'm trying to understand what is the issue there. Is there some code
I could run before I re-create the object in order to destroy the
previous instance ?

Not sure what you are trying to do.
Start by not using eval, no matter what your goal is.

/L
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,579
Members
45,053
Latest member
BrodieSola

Latest Threads

Top