Flylib.com

Books Software

 
 
 

7.9. Immutable Objects and Classes

 

[Page 232 ( continued )]

7.9. Immutable Objects and Classes

If the contents of an object cannot be changed once the object is created, the object is called an immutable object and its class is called an immutable class . If you delete the set method in the Circle3 class in the preceding example, the class would be immutable because radius is private and cannot be changed without a set method.

A class with all private data fields and no mutators is not necessarily immutable. For example, the following class Student has all private data fields and no mutators, but it is mutable.




public class


Student {



private int


id;



private


BirthDate birthDate;



public


Student(


int


ssn,


int


year,


int


month,


int


day) {
    id = ssn;

birthDate = new BirthDate(year, month, day);

}


public int


getId() {


return


id;
    }


public


BirthDate getBirthDate() {


return


birthDate;
    }
}



public class


BirthDate {



private int


year;


private int


month;


private int


day;



public


BirthDate(


int


newYear,


int


newMonth,


int


newDay) {

year = newYear;
     month = newMonth;
     day = newDay;
   }


public void


setYear(


int


newYear) {
     year = newYear;
   }
}



[Page 233]

As shown in the following code, the data field birthDate is returned using the getBirthDate() method. This is a reference to a BirthDate object. Through this reference, the year of the birth date is changed, which effectively changes the contents of the Student object.



public class


Test {


public static void


main(String[] args) {

Student student =


new

Student(


111223333


,


1970


,


5


,


3


);



BirthDate date = student.getBirthDate();


date.setYear(


2010


);


//Now the student birth year is changed!

}
}


For a class to be immutable, it must mark all data fields private and provide no mutator methods and no accessor methods that would return a reference to a mutable data field object.

 
 

[Page 233 ( continued )]

7.10. Passing Objects to Methods

So far, you have learned how to pass arguments of primitive types and array types to methods. You can also pass objects to methods. Like passing an array, passing an object is actually passing the reference of the object. The following code passes the myCircle object as an argument to the printCircle method:



public class


TestPassObject {


public static void


main(String[] args) { Circle3 myCircle =


new


Circle3(


5.0


);

printCircle(myCircle);

}


public static void



printCircle(Circle3 c)

{ System.out.println(


"The area of the circle of radius "


+ c.getRadius() +


" is "


+ c.getArea()); } }


Java uses exactly one mode of passing arguments: pass- by-value . In the preceding code, the value of myCircle is passed to the printCircle method. This value is a reference to a Circle3 object.

Let us demonstrate the difference between passing a primitive type value and passing a reference value with the program in Listing 7.6.

Listing 7.6. TestPassObject.java
(This item is displayed on pages 233 - 234 in the print version)
1


public class


TestPassObject { 2

/** Main method */

3


public static void


main(String[] args) { 4

// Create a Circle object with radius 1

5 Circle3 myCircle =


new


Circle3(1); 6 7

// Print areas for radius 1, 2, 3, 4, and 5.

8


int


n =


5


; 9

printAreas(myCircle, n);

10 11

// See myCircle.radius and times

12 System.out.println(


"\n"


+


"Radius is "


+ myCircle.getRadius()); 13 System.out.println(


"n is "


+ n); 14 } 15

[Page 234]
16

/** Print a table of areas for radius */

17


public static void



printAreas(Circle3 c,


int


times)

{ 18 System.out.println(


"Radius \t\tArea"


); 19


while


(times >=


1


) { 20 System.out.println(c.getRadius() +


"\t\t"


+ c.getArea()); 21 c.setRadius(c.getRadius() +


1


); 22 times ” ”; 23 } 24 } 25 }

The program passes a Circle3 object myCircle and an integer value from n to invoke printAreas(myCircle, n) (line 19), which prints a table of areas for radii 1 , 2 , 3 , 4 , and 5 , as shown in Figure 7.16.

Figure 7.16. The program passes a Circle object myCircle and an integer value n as arguments to the printAreas method, which displays a table of the areas for radii 1 , 2 , 3 , 4 , and 5 .


Figure 7.17 shows the call stack for executing the methods in the program. Note that the objects are stored in a heap.

Figure 7.17. The value of n is passed to times , and the reference of myCircle is passed to c in the printAreas method.

When passing an argument of a primitive data type, the value of the argument is passed. In this case, the value of n ( 5 ) is passed to times . Inside the printAreas method, the content of times is changed; this does not affect the content of n . When passing an argument of a reference type, the reference of the object is passed. In this case, c contains a reference for the object that is also referenced via myCircle . Therefore, changing the properties of the object through c inside the printAreas method has the same effect as doing so outside the method through the variable myCircle .