(syllabus and calendar)
|
Session 3 Lecture Notes for First Course in Java |
Just as the System.out object has a method for printing to the screen, so the
System.in object has a method for reading keyboard input.
Note: 13 is the integer value of the Enter key.
Syntax for the if, else if, else sequence.
Normally, the switch statement include break to exit when the awaited condition is met. The default statement executes if no case statement matches the value of the variable. The value of the case can be integer, character, short, or byte.
It is difficult to think of a use case that never uses break.
You can group adjacent case values
Control statements (if, loop, case in switch) permit nesting.
Infinite loop that tests for a particular character.
This do while loop uses escape sequences for carriage return (\r) and line feed (\n). A do while loop always executes at least once because it does not check its condition until the end.
Using continue in an infinite loop (line 21 goes to line 12) to force another iteration of the loop while ignoring the following statements inside the loop. The character values comes from the ASCII table.
Illustrate a combination of the features.
This for loop uses a double instead of an integer.
Using continue inside a nested for loop and using a label for continue.
Monitoring two counters in a for loop
What is another way to write the following? sum += i++;
A Help system with an infinite loop
A lot of work done with only a few lines of code.
Let's rewrite this while loop as a for loop.
Use a while loop nested inside a for loop
|
Type Casting
Main: Driver for Other Classes Singleton: private constructor |
Casting is the explicit translation of:
In a cast, the Java runtime knows enough about the types and how they are related to do this conversion.
byte, short, int, long, float, double | cast to/from | byte, short, int, long, float, double |
A widening cast is from a smaller type to a larger type.
A cast from a larger type to a smaller type must be explicit.
The syntax is (targetTypename)valueToCast
Line 9 casts the product of two doubles as an integer.
The output is:
The product as double is 3.75 The product as integer is = 3
Another explicit cast is of integer into byte:
b = (byte) (50 * 2);
Booleans cannot be cast.
When you cast a floating point type to an integer type, or a double to a
float, loss of precision might occur.
For example, (int)3.2
truncates the .2 and returns 3.
Also, when you cast from a larger integer type to a smaller one, if the number
is very large, it might be truncated and return a smaller number, or even wrap
around (as byte does) to its beginning.
The output is:
Conversion of int to byte. When int i = 258 is cast as a byte, the byte value is: 1 Conversion of double to int. Truncation when double 323.142 is cast as int: 323 Conversion of double to byte. Casting double 323.142 into byte causes wraparound after 255: 67
Note: Just imagine the porting issue if different platforms dealt differently with the issue of overstepping the limit of the byte data type. One platform might convert the byte back to a double. Another might assign a value of zero. Another platform might crash the program. Still another might hang.
You can cast an object to another class if the two classes are related by inheritance.
For example, all objects inherit from the superclass
Object.
http://java.sun.com/j2se/1.4.1/docs/api/java/lang/Object.html
Therefore, all objects have a GetClass()
method.
http://java.sun.com/j2se/1.4.1/docs/api/java/lang/Object.html#getClass()
I do not need to make an explicit cast for my string object--in this case the command line array of strings, or string array--to use methods it inherits from its superclass(es).
The output is:
The class of [Ljava.lang.String;@108786b is [Ljava.lang.String;
The class of java.lang.Object@119c082 is java.lang.Object
Another example in which we create a custom object type.
You do not need an explicit cast when upcasting objects, but you do need an
explicit cast when downcasting
objects.
For example, this example casts an object as a string.
Object is higher in the class hierarchy than String, so casting an object as a
string is downcasting.
String s = "Heeeeeeeeere's Johnny"; Object o = s; // implicit upcast, no casting syntax needed because all strings inherit from the Object superclass String sz = (String)o; // explicit downcast, need casting syntax because String is a subclass of Object
You can use the instanceof operator to test an object's class before doing a downcast:
String s = "Heeeeeeeeere's Johnny"; Object o = s; String sz; if (o instanceof String) { sz = (String)o; }
The instanceof
operator tests whether its first operand is an
instance of its second.
op1 instanceof op2
op1
must be the name of an object and op2
must be
the name of a class. An object is considered to be an instance of a class if
that object directly or indirectly descends from that class.
http://java.sun.com/docs/books/tutorial/java/nutsandbolts/other.html
Here, the instanceof operator determines
whether its first operand is an instance of its second operand.
The output is:
null true
false
true
We have seen casting among the primitive types, such as between
int and double,
which are related as primitives.
We also saw that all object are related, which enables upcasting and downcasting
among them.
Converting is the translation between unrelated types, that is, of a primitive
type to an object type, or of an object type to a primitive type, which you cannot do
by casting.
Unlike a cast, the runtime does not know enough about the types to do this
automatically.
Some code must be written to handle the conversion
Suppose that you have been storing zip codes as strings (which are objects in
Java), but now you need to
treat those zip codes as integers so that you can sort them as numbers more
effectively.
You can use an method of the Integer class to pass in a string argument and get
integer output.
In effect, the following example converts a
string object into a
integer
primitive.
or
String stringZipCode = "94568"; // stringZipCode is a String object int intZip = Integer.parseInt(myZipCode); // intZip is a primitive
http://java.sun.com/j2se/1.4.1/docs/api/java/lang/Integer.html
Each primitive type has a corresponding "wrapper" class. Why?
To convert an integer primitive into an object of its corresponding Integer class:
The output is:
The class of which 90103 is an instance is java.lang.Integer
http://java.sun.com/j2se/1.4.1/docs/api/java/lang/Integer.html#Integer(int)
The most common type of conversion is to and from a String.
The java.lang.Object package defines the
toString() method with a simple default
implementation.
Many classes override this implementation to provide a translation that
preserves the object's content.
For example, an XML document might use the toString()
method.
Suppose you want to convert the user's command line argument into an integer.
user_input = Integer.parseInt(args[i]); // compare new input argument with current max number if (user_input > max_number)
java.lang.Object defines an
equals() method, but the default implementation
is simply a = = test.
When you compare Strings, the = = operator tests for
identical objects.
More likely, you want to test for identical values
being stored in the String variables.
Every String object has an equals() method for this
test of equivalent values being stored in two string variables.
Whereas line 5 creates a second reference (or variable) to the original object, line 15 reassigns that variable to a new and different object.
The output is:
Contents of s1: Jimi Hendrix Contents of s2: Jimi Hendrix Do s1 and s2 refer to the same object? use s1 == s2) true Do s1 and s2 have equivalent values? use s1.equals(s2) true You created a new s2 and assigned it the value of s1, so s2 now refers to a different object even if the values are equivalent. Contents of s1: Jimi Hendrix Contents of s2: Jimi Hendrix Do s1 and s2 refer to the same object? use s1 == s2) false Do s1 and s2 have equivalent values? use s1.equals(s2) true
Java can "promote" data types when it evaluates an expression.
As the comments state, a byte can be promoted to a float, a char to an integer, a short to a double, an int to a float, and a float to a double.
How many arrays are in this photograph?
An array stores multiple variables
Examples of arrays
http://www.developer.com/java/other/article.php/1268901
Array objects encapsulate a group of variables, which don't have individual
names. They are accessed using positive integer index values. The integer
indices of a Java array object always extend from 0 to (n-1) where
n is the length of the array encapsulated in the object.
TIP: Remember that in Java, an array is
zero-based, and if you try to access an array of, say, 5 elements at the 5th
index, well, there is no 5th index, only 0 through 4.
Line 4 declares the array named month_days to store a set of values of type int.
Line 5 creates the array with 12 elements.
Lines 6 through 17 populate the array with integer values.
Line 19 gets the number of elements in an array by using the static variable
length of the array object.
Arrays are useful for many things. An array is a collection. One use of an array is as the return value of a method. In Java, a method can only return one value or object. What if you method calculates two or more values? It is possible to have the method return a collection object that contains multiple values (or objects).
The output is:
By the way, there is more than way to create an array:
In the example above, how does Java know the length of the array of friends?
The output is:
I never assigned the value of null of the String at index 3. How does Java determine the value is null?
What kind of array does the following photograph show?
One way to perceive the bowling pins is as a ragged array (4, 3, 2, 1). Another way is to see a 4x4 array with some nulls indices.
Internally, a String is an array of characters, an array of char. The Java API, however, considers a String to be an object. Therefore, you benefit from built-in methods and property to help you handle strings. Let's look at the methods available to every string in the APIs.
Here is some starter code for taking command-line input:
So we know that an array can store many value of one, and only one, type.
What if we want a way to associate values of different types?
An object is not an array, and not even a multi-type array, but an object does
allow us to get and set a multiple types.
An object is surely less primitive than a "primitive", and perhaps closer to
real-world objects insofar as it can be more complex.
An object is a custom data-type that can have both data and behavior.
Sun's tutorial on object-oriented programming concepts: http://java.sun.com/docs/books/tutorial/java/concepts/index.html
[A good, easy-to-read introductory book with many diagrams: Object Technology: A Manager's Guide by David Taylor. http://www.bookpool.com/.x/49jdnnq9t0/sm/0201309947 ]
Procedural languages, such as C, center around code, and what the code does. To write procedurally, you have to think like a computer.
Object-oriented languages, such as Java, center around objects, which is more like how human beings understand the world. For example, you can model your program on how you model your business, with objects such as Customer, Salesperson, Product, Order, Account. Objects are at a higher level than routines. Objects involve the abstraction of details. You design an object-oriented system by thinking about self-enclosed, discrete entities (objects) that send messages to each other.
[Note: Some Java applications serve a business workflow based on a business model of business objects. Corresponding to each business object (Customer, Salesperson, Order) can be a database table, which in term corresponds to a Java object that contains the business logic for that business object. In such a scenario, a database field (table column), such as Name or ZipCode can correspond to an object attribute or property.]
The three key concepts of object-oriented programming are:
Encapsulation is like a capsule: the doctor tells you to take a medicinal capsule or pill. Far too small for you to see is the structure of the compound or molecule that does work in your bloodstream or organs to cure your disease. You don't even see the components of the mixture, which might be white medicine mixed with, say, green flour. The complexity is hidden from you. Your orders are simple and external to the encapsulation: take one green pill each day with water.
Encapsulation is like a black box. When you purchase a television set, you do not need to know the details of the electronics inside (raster-scanning cathode ray tube with magnetic electron gun, alternating current transformer, hundreds of capacitors, thousands of transistors). Instead, you only need to know how to plug in the UNIT, attach the cable, turn the on switch, and press buttons on the remote control. You have a UNIT that sends visual and audio messages to you, and you do not care about the hidden actions within the unit.
In Quality Assurance, the phrase "black box testing" means observing the behavior of the unit from outside, without having access to the internal source code.
(Philosophically speaking, even if we say we "know" a person, we do not know the details that are internal to that person, only the messages that the self-encapsulated "person unit" makes accessible or public in some way, such as through words or deeds. Even within the electronics of our own nervous system, an encapsulated program regulates our heartbeat without our conscious control. The messaging between brain and heart is hidden from us. That's probably a good thing, if we want to avoid information overload!)
In Java, the unit of encapsulation is the class. Each object is an instance of a class. The class is a template for making objects. The class is similar to a cookie cutter, or a mold, for making things of a certain shape, things with certain attributes. If I define a class called dog, it might have an attribute for number of legs, which might be set to four:
int numberOfLegs = 4;
(When I go to the pet store to buy a dog, I do not purchase the class of Dog. Rather, I purchase an instance (an embodiment) of the class Dog. I purchase Fido, Rover, Lassie or another actual dog to whom I might have not yet have assigned a name.)
Back to the class of Dog (that is, to dogs in general).
Unless I only want a statue of a dog, I want the dog to be able to do things.
The dog class might have an action (or behavior, or method) for wagging its
tail, which we can call the wagTail() method, and another action for bringing me
the morning newspaper, the fetchPaper() method, or the barkAtStranger()
method,
or the eatFoodBeforeAnotherDogCanStealIt() method that distinguishes the class
Dog from the class
Cat that has its
eatFoodNibbleByNibbleAsOccasionalSnack() method.
I do not care about the bio-electro-chemistry that makes the tail muscles
contract and produce tail wagging. I just want to see my dog happy, tail
a-wagging.
I do not care about the intricate machinery in the dog's nose that enables the
dog's identifyAnythingWithinTwoSecondsBySent() method. I just want my dog to recognize me at night, even
in darkness, without barking at me and biting me.
if (identifyAnythingWithinTwoSecondsBySent() ==
"stranger") {
bark();
bite();
}
if (identifyAnythingWithinTwoSecondsBySent() == "owner" || "friend") {
wagTail();
}
Encapsulation simplifies things for whatever communicates with the encapsulated object. The internals can change without affecting the overall behavior. For example, the interface to a piano is a set of piano keys and three pedals. Behind the scenes, inside the black box of the piano, are sophisticated mechanical hammers, springs, and strings. If you can play a cheap, honky-tonk, out-of-tune piano, you can also play the world's most expensive Steinway concert piano, and without having to understand Steinway's patented hammer action. Indeed, I can then also play an electric or electronic piano (or even pick out a tune on a vibraphone, xylophone, or glockenspiel), which might be a unit that encapsulates different methods than hammers striking strings, yet offer me the same user interface of a set of PianoKey objects. I can re-use my code that tracks the notes of scale, no matter which keyboard instrument I play.
Where is the messaging in this piano metaphor?
Inheritance enacts the reuse of code. For example, now that I have a messaging system for the middle C key, I can reuse that logic for all 88 keys on the piano. Each key can inherit attributes (properties) and behavior (methods) from the PianoString class, the template or mold for all strings.
When you design a more complicated system, your class hierarchy will have more levels. For example, if you were designing a library catalog, you might layers such as these:
LibraryObject
LoanObject vs ReferenceObject
Periodical vs Book vs AudioTape vs VideoTape vs DVD
DailyPeriodical vs MonthlyPeriodical
ForeignLanguageMonthlyPeriodical vs EnglishMonthlyPeriodical
AsianLanguageMonthlyPeriodical vs EuropeanLanguageMonthlyPeriodical
JapaneseMonthlyPeriodical vs ChineseMonthlyPeriodical
All the objects in the hierarchy inherit a characteristic from the LibraryObject, that is, belonging to the library.
All the objects for loan, unlike the reference objects, can be "checked out" to customers.
All the periodicals, unlike books and such, are published on a recurring basis.
Therefore, whatever object is a member of the JapaneseMonthlyPeriodical class, will automatically inherit the logic common to LoanObject, that is, the ability to be "checked out". I do not have to rewrite the logic for the procedure of checking out a JapaneseMonthlyPeriodical and make it different from the procedure for checking out a EuropeanLanguageMonthlyPeriodical. It is like inheriting money or kingship: I do not have to do work to get the money or the crown.
However, it might WANT to over-ride what an object inherits. For example, I might want the checkout period for AsianLanguageMonthlyPeriodical to be shorter or longer than for EuropeanLanguageMonthlyPeriodical. In other words, I might want to have different styles or forms of checkout rules. The ability to have many (poly) forms (morphs) is called polymorphism.
Suppose you have a class hierarchy involving three classes, Circle, Square, and Rectangle, which all inherit the calculateArea() method from the Shape interface. Polymorphism in the sense of an interface enforces that each class implementation has a calculateArea() method, but allows each implementation class redefine the required method to fit the shape. For example,
class Circle implements Shape {
public double calculateArea() {
circleArea = pi * radius * radius;
return circleArea;
}
}
class Triangle implements Shape {
public double calculateArea() {
triangleArea = base * (height/2);
return triangleArea;
}
}
Polymorphism means "many forms". A behavior or method can have more than one
form.
eatFood(chopsticks); // typical of China
eatFood(fork, knife); // typical of French nobility
eatFood(rightHand); // typical of Morocco
eatFood(rightHand, leftHand); // typical of baseball stadium hotdog devotees
A case of polymorphism could be in banking. Suppose that my bank allows me to open two kinds of accounts: a standard account that only requires a minimum balance of one cent (but charges service fees), or a deluxe account requires a minimum of one thousand dollars (and provide services without fee). Therefore, the openAccount() method has two forms or two signatures.
if (deposit => standardMinimum | deposit <=deluxeMinum)
{
StandardAccount.openAccount();
}
else
{
DeluxeAccount.openAccount();
}
[Sneak Peek to a more detailed introduction to Object-Oriented Programming (OOP) and two sample programs with a simple class called Box]
INTRODUCTION: A class is the basic form of encapsulating the logic of an object-oriented program. The compilation unit assumes the existence of a class. The compiler outputs a class file. Let's look at what is a class by looking at the example of a box.
Just as integer (int) and boolean are data types, so each object is an
instance of a particular class.
The class to which an object belongs is its type.
When you define a class, you are essentially creating a custom data type.
(In this sense, object-oriented programming allows you to extend the programming
language!)
Each an every object is an instance of a class. A class is a template for creating objects.
A class has attributes (properties) and behavior (methods).
The Unified Modeling Language (UML) is an industry-standard set of
conventions for designing and analyzing classes.
Note in the diagram below the convention of putting the class name at the top,
followed by a section for properties (nouns), and at the bottom a section for
methods (verbs).
http://www.agilemodeling.com/style/classDiagram.htm
(If you are interested in UML, see http://www.rational.com/uml/leaders/index.jsp)
What does the following code snippet do?
class Box { double width; double height; double depth; }
In the class declaration, we create no object! There is only logic, no embodiment, no instance.
Because Java is a strongly-typed language, we need to declare the data type
of each instance variable in a class.
And, each instance (each object) of the class has its own copy of the classes
instance variables.
Think of it this way: if I have a blueprint for a house with three bedrooms and
two bathrooms, each house I build with the blueprint will have three bedrooms
and two bathrooms.
Box myBox; // creates an instance variable that holds the value null
mybox = new Box(); // calls the constructor and allocates memory to a new object (instance) // that inherits the properties and methods of the class template
Note: The primitive data types, such as int, do not require the new operator
because they are not objects. Indeed, they store their value directly.
However, a string is an object, yet you have declared
String myString without having to use the new
operator.
This is a convenience to you.
We saw already that two String objects are two separate objects, even if they hold the same value.
This like saying:
Box b1 = new Box(): Box b2 = new Box();
On the other hand, if we say
Box b1 = new Box(); b2 = b1;
then b2 refers to the same single box object that b1 does.
Because there are two references to one object, either "handle" can modify the
object they both point to.
What happens if we now say this:
Circle b2 = new Circle();
Do b2 and b1 still point to the same object, or has the most recent
assignment pointed the two instance variables to different objects?
Do b2 and b2 still refer to objects of the same type or class?
Let's examine this example.
The output is:
Volume is 3000.0 Volume is 162.0
This example both defines a class and a method for that class.
Which instances of the class inherit the method?
What is going on in this example?
Let's examine the parameters to the method that sets the dimensions of the box.
The class is a unit for encapsulation.
A class has methods and attributes
In Java, the unit of encapsulation is the class. Each object is an instance of a class. The class is a template for making objects. The class is similar to a cookie cutter, or a mold, for making things of a certain shape, things with certain attributes. If I define a class called dog, it might have an attribute for number of legs, which might be set to four:
int numberOfLegs = 4; // this attribute could be private or public - if hidden, it's more encapsulated?
A string is implemented inside Java as an object of the class String. Therefore, a string object has the length method.
I don't need to know how the length method works. The details are encapsulated in the class that defines the method.
Encapsulation supports re-use of code (or patterns), especially when I combine encapsulation with inheritance.
The subclass is a unit for inheritance (from its superclass).
The method is a unit for polymorphism.
Let's look at an application that uses a switch.
What is a switch statement about? What is it an alternative for?
What datatype does the isvalid boolean method of line 57 require?
Why does the return value of the read method undergo a cast in line 74?
Where does the hlpobj object get the showmenu method?
What is going on in line 74? What is the Java buzzword for a method having multiple implementations? What buzzword of object-oriented programming does this correspond to?
http://java.sun.com/j2se/1.4.1/docs/api/java/io/InputStream.html#read()
Use the following class as a template to experiment with
making your own classes.
One possibility: Shape, and then “class Circle extends Shape” to calculate area
and perimeter.
// This program uses a parameterized method. class Box { double width; // declare double height; double depth; // compute and return volume double volume() { // declare a method return width * height * depth; } // sets dimensions of box void setDim(double w, double h, double d) { // defining width = w; height = h; depth = d; } } class BoxDemoParam { public static void main(String args[]) { Box mybox1 = new Box(); // create a box object Box mybox2 = new Box(); // create another box object double vol; // initialize each box mybox1.setDim(10, 20, 15); mybox2.setDim(3, 6, 9); // get volume of first box vol = mybox1.volume(); System.out.println("Volume is " + vol); // get volume of second box vol = mybox2.volume(); System.out.println("Volume is " + vol); } }
How can I create a class that is guaranteed to have only one instance. Such a class/object is known as a singleton. http://www.javaranch.com/newsletter/July2003/SaloonQnAOfTheMonth.html