We closed this forum 18 June 2010. It has served us well since 2005 as the ALPHA forum did before it from 2002 to 2005. New discussions are ongoing at the new URL http://forum.processing.org. You'll need to sign up and get a new user account. We're sorry about that inconvenience, but we think it's better in the long run. The content on this forum will remain online.
IndexProgramming Questions & HelpSyntax Questions › Passing arguments by reference or by value
Page Index Toggle Pages: 1
Passing arguments by reference or by value (Read 777 times)
Passing arguments by reference or by value
Jun 7th, 2009, 2:52pm
 
I feel like I should ask the expert instead of guessing. I wonder how processing passes arguments to functions. Does it do it by value or by reference? Or does it pass by value for variables and by reference for arrays? Thanks. Is there a way to control which to choose?
Re: Passing arguments by reference or by value
Reply #1 - Jun 7th, 2009, 3:51pm
 
I was not specific. Here's what I did:

I'm trying to pass an array of objects to a function and it then appends a new object to the array. I always find my object array with zero length in draw() and the object array with size 1 in the function, every time I call. Can someone tell me what I did wrong? I thought since the array is an object, its reference is passed to the function and the append will add to the original array object. Thanks.

object1 mylist[]={};
void function1 (object1[] listofobjects)
{
listofobject=(object1[]) append(listofobject,new object1 tempObj);
}

void draw()
{

function1(mylist);
function1(mylist);
function1(mylist);
}
Re: Passing arguments by reference or by value
Reply #2 - Jun 7th, 2009, 5:23pm
 
Primitives (an int, byte, etc.) are always passed by value:
Code:
int a = 4;
int b = 6;

a = b; //copy the value only

a++;
println(a); //will print 7
println(b); //will print 6

While Objects are passed by a reference. The reference that you use within the function, though, is a copy of the reference.
Code:
//If you are used to c/c++, a reference isn't much different from a pointer.

RefTest a = new RefTest(5);
RefTest b = new RefTest(4);

void setup() {
 println(a.val); //shows 5
 println(b.val); //shows 4
 
 test(a);

 
 a = b;
 println(a.val); //will show the same value (4)
 println(b.val); //because a and b point to the same object
}

void test(RefTest tst) {
 
 //you can affect the original value by doing this
 tst.val = 7;
 //because tst holds a reference to 'a'
 
 //but if you do
 tst = new RefTest(2);
 //you make tst point to a new object, leaving the original alone
 
 println(tst.val); //shows 2
 println(a.val); //shows 7
}

class RefTest {
 int val = 0;
 
 RefTest(int v) {
   val = v;
 }
}

Maybe a little overkill for an explaination...
You would probably use a function that returns a new array instead of void.
Code:
myArray = arrFunction(myArray);
...
object1[] arrFunction(object1[] source) {
 return (object1[])append(source,new object1 tempObj);
}
Re: Passing arguments by reference or by value
Reply #3 - Jun 7th, 2009, 6:10pm
 
NoahBuddy,

Thanks for the example. I was catching up on my java reading. According to sun, java passes object or array by reference. So I should be able to append to the array by means of the copy of the reference. On the other hand, I tried the following:
Create one element in setup and draw keeps printing the length of the array, 1. Then add one element in the function and keeps printing the length of the parameter and the original array (defined outside draw). To my biggest surprise, the original array size is always one in the draw and in the function. The copy (parameter passed to function) is 2, due to append. I thought java passes array by reference, maybe array of object is different, the appended object somehow associates with the copy reference in the function!?
Re: Passing arguments by reference or by value
Reply #4 - Jun 7th, 2009, 6:39pm
 
Well, not exactly.

When you use "object1 mylist[]={};" you create an empty array.

If you had something in it before the call to the function, there would still be something there.

Inside the function there are two variable names that point to the same object (or array): mylist and listofobjects. And when you assign the local variable (listofobjects), you are only telling it to point to something else.

After the function returns, the local variable listofobjects is destroyed. The data it pointed to is still referenced by mylist. Since listofobjects had been assigned to a new array (output of append), the data it pointed to is left to the garbage collector.
Re: Passing arguments by reference or by value
Reply #5 - Jun 7th, 2009, 8:03pm
 
Wow, thanks a lot. I didn't have enough background on java. I'll read about garbage collection more. I always have a fear that some of my code creates garbage and I want to know what action creates them. Like you said the append returns a new array and the old one is then garbaged. What book/resource do you suggest someone to read about garbage disposal? Thanks again.
Re: Passing arguments by reference or by value
Reply #6 - Jun 7th, 2009, 10:15pm
 
One more thing real quick: say I have an array of objects myList, I then want to empty the array.

I) I can use shorten() until the array is zero in length.
II) I can also assign an empty object array to myList, say object empty[]={}; myList=empty;

If I do II does the garbage collector take my previous array of objects and dispose of all the objects? Which way would you prefer? Could you suggest an even better way? Thank you.
Re: Passing arguments by reference or by value
Reply #7 - Jun 7th, 2009, 11:00pm
 
I don't really know what books to recommend for Java. I've had one class on Java and have an outdated book on making animations on applets. I actually didn't get into the language until I started using Processing.

For Processing (without the stuff Java does in the background) I would recommend checking out http://www.learningprocessing.com/

I can't say I know the best ways of helping the garbage collector out but a few ideas:

You could use shorten. If you don't know the number of objects you will have, it may be easier to use a prebuilt class like ArrayList to add and subtract items. http://processing.org/reference/ArrayList.html

If your program is going to be running for a while and is adding and removing objects, I would set any references that are no longer used to null. Such as myArray = null;

If you are reusing an array like myArray = append(...);
you don't have to worry about making it null first.

In most cases, the JVM will handle the garbage by itself. Local variables will get recycled and anything you create while running should be cleaned up eventually when you exit the program. I suppose there are cases with circular references, but I don't want get into too much more than I have. :]
Re: Passing arguments by reference or by value
Reply #8 - Jun 8th, 2009, 12:14am
 
One fact you might not know (I only skimmed the thread...):
array's length is immutable.
The Array Functions provided by Processing are convenient and easier to use than Java Collections, but when they need to grow an array, they "cheat": they make a bigger array and copy data (references) from the old one to the new one. So even if arrays are passed by reference, if you use append(), you won't have the same array so the original one won't be modified!

For such usage, you should use ArrayList.
Re: Passing arguments by reference or by value
Reply #9 - Jun 8th, 2009, 11:33am
 
Thanks NoahBuddy and PhiLho. You guys gave me many great tips. I'll think about overhauling my 2000 line code with array lists:(. That seems to be more efficient. Yes, I just read about java and sun says arrays are fixed in length so as the strings. I was wondering what the heck with processing. PhiLoh, I guess you just knew what I was about to ask even I did ask yet. Thanks again.
Page Index Toggle Pages: 1