byVal equivalent for JavaScript?

N

neerolyte

How would I pass an object variable to a function without that variable
getting changed in the function changing the variable that was passed (eg
both variables treated as one)?

<script>
var a = 1;
var b = 2;
function sub(a, b)
{
a = a - b;
return a;
}
document.write("a = " + a + "<br>");
document.write("b = " + b + "<br>");
document.write("sub(a, b) = " + sub(a, b) + "<br>");
document.write("a = " + a + "<br>");
document.write("b = " + b + "<p>");

var a = new Object();
a.val = 1;
var b = new Object();
b.val = 2;
function subo(a, b)
{
a.val = a.val - b.val;
return a.val;
}
document.write("a = " + a.val + "<br>");
document.write("b = " + b.val + "<br>");
document.write("subo(a, b) = " + subo(a, b) + "<br>");
document.write("a = " + a.val + "<br>");
document.write("b = " + b.val + "<br>");
</script>

the above script outputs:
a = 1
b = 2
sub(a, b) = -1
a = 1
b = 2
a = 1
b = 2
subo(a, b) = -1
a = -1 <= I want this to still be 1
b = 2


thanks in advance
 
E

Erwin Moller

neerolyte said:
How would I pass an object variable to a function without that variable
getting changed in the function changing the variable that was passed (eg
both variables treated as one)?

<script>
var a = 1;
var b = 2;
function sub(a, b)
{
a = a - b;
return a;
}
document.write("a = " + a + "<br>");
document.write("b = " + b + "<br>");
document.write("sub(a, b) = " + sub(a, b) + "<br>");
document.write("a = " + a + "<br>");
document.write("b = " + b + "<p>");

var a = new Object();
a.val = 1;
var b = new Object();
b.val = 2;
function subo(a, b)
{
a.val = a.val - b.val;

This is your problem.
Over here you change the value of val in Object a.
What do you Javascript expect to do?
Why did you code that line?

Why not remove that line and just return?
return a.val - b.val;

That should work.

Regards,
Erwin Moller
 
N

neerolyte

This is your problem.
Over here you change the value of val in Object a.
What do you Javascript expect to do?
Why did you code that line?

Why not remove that line and just return?
return a.val - b.val;
no, because this is just demo code to demonstrate the problem, the real code
has just made it to 310 lines, so i figured it wouldn't be nice to post it,
i have a solution that involves making a new object, and transfering all the
values individualy, this works but seems rather pointless if there is
something equivalent to byVal
 
B

Brian Genisio

neerolyte said:
no, because this is just demo code to demonstrate the problem, the real code
has just made it to 310 lines, so i figured it wouldn't be nice to post it,
i have a solution that involves making a new object, and transfering all the
values individualy, this works but seems rather pointless if there is
something equivalent to byVal

I have never met a language that it is a good idea to pass any large
object or structure by value. If your object is of any size, you
_should_ be passing by reference, and scrap the idea of passing it by
value.

Brian
 
N

neerolyte

I have never met a language that it is a good idea to pass any large
object or structure by value. If your object is of any size, you
_should_ be passing by reference, and scrap the idea of passing it by
value.
the objects consist of an array of numbers, (array varies in size from 1 to
40 in length, average around 20), and a true or false value.
I don't think this is particularly large, but atleast one of the functions
needs to have the original values that were passes to it, close to the end
of it, so passing by referance is out of the question.



p.s. i did mean to send this to the news group and not just you Brian,
sorry.
 
B

Brian Genisio

neerolyte said:
the objects consist of an array of numbers, (array varies in size from 1 to
40 in length, average around 20), and a true or false value.
I don't think this is particularly large, but atleast one of the functions
needs to have the original values that were passes to it, close to the end
of it, so passing by referance is out of the question.



p.s. i did mean to send this to the news group and not just you Brian,
sorry.

The rule I follow: If the data I am passing to a function is any larger
than the size of a pointer (If the language even has one), I always pass
by reverence or by pointer.

Something with 20 items is really large to pass on the stack. The
compiler will make a copy of it anyways, when you pass by reference, so
if you really need to make a copy of the data when it comes, you are not
doing anything out of the ordinary. Making a copy of an array only
takes two lines anyways, so why not just make a copy when you get the
array passed to you?

I have never encountered a language that lets you pass an array, and all
of it's elelments by value.

Here, in Javascript, you are sending an Array object over... if it is by
reference, or by value, it does not matter, since any object in the
array is referenced by the Array object... In other words, A reference
to an Array Object, or a copy of an Array object will always point to
the same set of objectes within the Array object.

If you need to modify the array AND use the original values in the
array, after they have been modified, you NEED to make a copy of it.

I know it is not the answer you are looking for, but there really is no
other way.

Brian
 
N

neerolyte

The rule I follow: If the data I am passing to a function is any larger
than the size of a pointer (If the language even has one), I always pass
by reverence or by pointer.

Something with 20 items is really large to pass on the stack. The
compiler will make a copy of it anyways, when you pass by reference, so
if you really need to make a copy of the data when it comes, you are not
doing anything out of the ordinary. Making a copy of an array only
takes two lines anyways, so why not just make a copy when you get the
array passed to you?

I have never encountered a language that lets you pass an array, and all
of it's elelments by value.

Here, in Javascript, you are sending an Array object over... if it is by
reference, or by value, it does not matter, since any object in the
array is referenced by the Array object... In other words, A reference
to an Array Object, or a copy of an Array object will always point to
the same set of objectes within the Array object.

If you need to modify the array AND use the original values in the
array, after they have been modified, you NEED to make a copy of it.

I know it is not the answer you are looking for, but there really is no
other way.

Brian
thankyou for your time and patience, i have not ye, but i will modify the
functions to not use my pass by val work around.
thanks for the tips
 
M

Martin Honnen

Brian said:
I have never encountered a language that lets you pass an array, and all
of it's elelments by value.

Off topic here, but PHP (4 at least) will pass arrays by value (unless
you explictly pass by reference).
 
T

Thomas 'PointedEars' Lahn

neerolyte said:
How would I pass an object variable to a function without that variable
getting changed in the function changing the variable that was passed (eg
both variables treated as one)?

If you pass a reference to a method and modify properties of
the reference, you modify the object that it references.

<script type="text/javascript">

is valid HTML 4.
var a = 1;
var b = 2;
function sub(a, b)
{
a = a - b;
return a;
}

This works and leaves "a" unchanged because "a" is the identifier of
a named function argument and thus a variable of the local execution
context (in short: a local variable). If you would have written
this.a instead, you would have referenced the global "a" if sub(...)
was not called as a method of another object than the global one.
var a = new Object();
a.val = 1;
var b = new Object();
b.val = 2;
function subo(a, b)
{
a.val = a.val - b.val;
return a.val;
}
[...]
document.write("subo(a, b) = " + subo(a, b) + "<br>");
[...]

This changes the value of a.val because you pass "a", a reference to
*a* global object (which is in fact a property of *the* global object),
as argument of the method. So the global "a" is assigned to the local
"a", thus it refers to the same object and the property of the object
it refers to, is of course changed by the assignment.

The solution is obvious: Do not assign anything to properties of
arguments if you want them unchanged. Instead, copy the value of
that property in a local variable and manipulate that variable,
*e.g.*:

function subo(a, b)
{
var x = a.val;
x = a.val - b.val;
return x;
}


HTH

PointedEars

P.S.: Your "From:" header is borken, read
<http://www.interhack.net/pubs/munging-harmful/>
 

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,577
Members
45,052
Latest member
LucyCarper

Latest Threads

Top