Wednesday, April 19, 2006

java

JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 1 - Introduction to JAVA??? (the Big picture) (V1.2.3)
PDF
Purpose
History Of Java
The Internet And The World Wide Web
JAVA And Its Write Once, Run Anywhere Philosophy
Conclusion
Purpose
The purpose of this document is to provide a bird's eye view of Java's scope and to provide a general context which illustrates what Java can be used for (this context is useful to have while learning the details of the language. You do not have to go to all of the links that are present in this document, just the one's that interest you (you can always refer back to this document later if you would like). It is my opinion that the best way to learn Java is to approach it holistically. By this I mean that you have to spend as much time trying to grasp the 'big picture' aspect of Java as you do learning the details of the language. I have found that the best way to get a handle on this big picture is to spend some time each day surfing the main Java web sites (links are provided at the end of this document) and reading various articles and news items that interest you.
Java is not just a language. Java is a software platform just like Windows and Linux are software platforms and so when one learns Java it is similar to learning something like VisualC++ and the Windows API at the same time. Therefore when I say 'Big' I think you will find that I am not understating this aspect of Java. The scope of Java is huge and it is going to take you a year or so of consistently surfing the Java web sites and reading articles and news releases before you start to become truly comfortable with Java's big picture. The nice thing is that the efficient management of massive amounts of complexity is what Java and object technologies were designed for so as you become comfortable with the Java and object oriented programming you will start to see how these tools can be applied to this vast scope in order to organize it, hide its details and allow one to deal with it from a high level of abstraction.
For this class spending some time trying to grasp Java's big picture is not an absolute necessity. If you follow the lectures, do the labs and focus primarily on the language itself, by the end of the class you will be developing mildly interesting Java programs with no problems. I do think, however, that any time that you spend trying to get a handle on Java's big picture is a wonderful investment that has a high probability of paying handsome dividends for many years to come. Just visit job sites like www.monster.com and look at the growing demand for Java developers or look for the increasing number of articles that talk about Java's dramatic rise in popularity for evidence of this.
This document begins by discussing the separate developments of object oriented programming, the internet and the world wide web because these influences were heavily drawn upon during the design of Java. The rest of the document describes some of the main areas that Java has been applied to since its official release in 1995. At the end of this lecture you will be directed to perform lab1 which consists of downloading and installing the Java Development Kit and some other tools that we will be using in this class. If you have any questions feel free to post them on the class forum.

History Of Java
Java's C Roots
Java has its roots in the C++ language and C++ has it roots in C so in order to understand Java it is helpful if one knows a bit about C. The C programming language was developed between 1969 and 1973 mainly for use as the systems programming language for the UNIX operating system. Between 1973 and the late 1980s many slightly incompatible versions of C were developed but finally in 1989 a standard version was approved by the American National Standards Institute which was called ANSI C.
C compilers convert C source code directly into native binary machine code that can be directly executed by the target computer's microprocessor. Binary code for one microprocessor, however, can not run on a microprocessor that uses a different design (for example Intel binary code will not run on a Motorola microprocessor). Even if the microprocessors are the same, if the operating systems they are running is different the binary code for operating system 1 will not run in operating system 2 (for example, Windows binary code will not run on Linux).
While C code is not portable at the binary level it is portable at the source code level which means that if a C program only used standardized libraries (utility procedures for commonly needed functionality like printing to a screen or reading from a keyboard) then the C source code to this program could be copied to a computer using a different microprocessor and/or operating system and the second computer's C compiler could compile this source code and generate a version of the program that would run on the different platform (UNIX and Linux use this source code portability feature of C very heavily).
Object Oriented Programming (OOP)
While procedural languages like C were being widely deployed and used throughout the 1960s and 1970s a new programming paradigm called Object Oriented Programming was being developed The first object oriented programming language was Simula and it was used as a base for XEROX's Smalltalk language and also for the object oriented version of C which is called C++.
OOP is a software design philosophy where software is modeled after the physical world. Object oriented programs are built using software objects which have attributes and behaviors. As a concrete example of this think of a typical office chair. The chair has attributes (color, number of wheels, material type) and behaviors (spin, roll, set height).
A software object's attributes are held in special variables called instance variables and its behaviors are determined by code which is held in methods (methods are similar to C Functions or BASIC Subroutines). After an object is created it is used by sending it Messages. In the case of the chair we could send it a chair.spin(3) message which would tell the chair to spin 3 times or a chair.setHeight(32) message which would tell the chair to set its height to 32 centimeters.
C++ was developed in the early 1980s and it added object oriented capabilities to the C language. C++ is backwards compatible with C which means that C++ compilers can be used to generate C only code and many ???object oriented??? C++ programs actually contain a mix of object oriented C++ and procedural C code.
Even though object oriented programming has been around since the 1960s it did not become widely used until the 1990s. During the 1990s C++ was increasingly used for large programming projects and Java also was developed during this decade.
SUN Microsystems starts an internal research project in 1991 called ???Green???
In 1991 Sun Microsystems became interested in developing software for the then emerging intelligent consumer electronics device market and they started a research effort called project 'Green'. Project Green resulted in a new C++ based programming language called OAK and this new name was inspired by the tree which grew outside the office window of James Gosling, Java's main developer. Unfortunately SUN discovered that there was already an existing programming language called OAK and the name Java was finally selected when the project Green team discussed alternative names in a local coffee shop. http://java.sun.com/people/jag/green/index.html
One of the main difficulties that intelligent consumer electronics devices present to software developers is that they use a large variety of microprocessors and operating systems which makes it very difficult to port applications between them. Java solved this problem by using a virtual machine which is a microprocessor implemented in software upon which Java machine code (called bytecode) runs. The idea was that Java virtual machines could be developed for the numerous microprocessors and operating systems that the various electronic devices were using and then a Java program could be written once and then run on each of these devices without recompiling.
Unfortunately the market for intelligent consumer electronics devices did not develop as quickly as anticipated and project Green was in danger of being canceled. Java was very close to dying a premature death when an astonishing world-shaking paradigm shift took place just in time to save it. Around 1993 the World Wide Web exploded in popularity and Java's developers saw that not only could consumer electronic devices host a Java virtual machine but so could web browsers.
The Java development team quickly developed a web browser that was capable of running Java code embedded in web pages (applets) and this idea was so popular that in May 1995 SUN officially announced the Java programming language (see http://java.sun.com/features/1998/05/birthday.html ).

The Internet And The World Wide Web
Since Java is the first widely adopted software platform that was specifically designed for the Internet and the World Wide Web a short discussion of these two technologies will help with understanding some of Java's design decisions.
How The Internet Started
In 1972 the first public demonstration of the ARPANET (Advanced Research Projects Agency Network) took place and its primary purpose was to investigate techniques for linking various types of packet networks together. http://www.isoc.org/internet/history http://www.internetvalley.com/intval.html
Throughout the 1970s and 1980s the number of nodes on the ARPANET grew at an increasing rate and eventually this network became known as the Internet. Up until 1991 the communications traffic on the Internet consisted primarily of emails, file transfers and various distributed applications (like multiuser role playing games). During this time the internet was mainly used by computing professionals because only people with fairly sophisticated computer skills were capable of accessing it. In order open the internet up to the rest of the world an abstract layer needed to be developed which would sit on top of the internet and shield users from the internet's complexity. This abstraction came into being in 1991 when the World Wide Web was created.
The World Wide Web Makes Using The Internet Easier
In the early 1990s the World Wide Web was developed by Tim Berners-Lee who at that time was a computing professional working at the CERN scientific research institute in Europe. The CERN institute was jointly funded by a number of European countries and these countries would send their scientists to the institute in or to conduct joint research projects. This arrangement turned out to be an excellent incubator for developing abstraction technologies to make accessing computer networks easier because of the difficulties involved in facilitating communications between scientists that spent part of their time at CERN and part of their time at their home institutions.
Tim Berners-Lee conceived of the World Wide Web abstraction and the technologies it would use (HTML and HTTP) in order to help solve the communications problems at CERN and these technologies eventually spread throughout the whole internet. In 1991 Tim Berners-Lee and CERN released the WorldWideWeb browser which uses HTTP (Hyper Text Transfer Protocol) to move data around the network and HTML (HyperText Markup Language) to markup this data for display on a Web Browser. http://www.w3.org/History.html
At first the world did not understand what was so useful about the World Wide Web but after an exhausting marketing effort by Tim Berners-Lee and the release of the first graphics-based Web browser (Mosaic) in 1993, people started to understand its usefulness and the World Wide Web's adoption rate after 1993 has been absolutely astonishing.
What Is The Difference Between The Internet And The Web?
???The Internet ('Net) is a network of networks. Basically it is made from computers and cables. What Vint Cerf and Bob Khan did was to figure out how this could be used to send around little "packets" of information. As Vint points out, a packet is a bit like a postcard with a simple address on it. If you put the right address on a packet, and gave it to any computer which is connected as part of the Net, each computer would figure out which cable to send it down next so that it would get to its destination. That's what the Internet does. It delivers packets - anywhere in the world, normally well under a second. Lots of different sort of programs use the Internet: electronic mail, for example, was around long before the global hypertext system I invented and called the World Wide Web ('Web'). Now, video conferencing and streamed audio channels are among other things which, like the Web, encode information in different ways and use different languages between computers ("protocols") to provide a service. The Web is an abstract (imaginary) space of information. On the Net, you find computers -- on the Web, you find document, sounds, videos,.... information. On the Net, the connections are cables between computers; on the Web, connections are hypertext links. The Web exists because of programs which communicate between computers on the Net. The Web could not be without the Net. The Web made the net useful because people are really interested in information (not to mention knowledge and wisdom!) and don't really want to have know about computers and cables.??? Tim Berners-Lee http://www.w3.org/People/Berners-Lee/FAQ.html
What Is A Web Server?
A server is either a program or a hardware device that is connected to a communications network and services requests from clients. A file server makes files accessible to client computers usually on a Local Area Network (LAN). An email server handles email requests for email clients. Web servers make HTML files, graphics images, sounds, etc. available to Web browsers (clients) over LANs or the internet.
A Web server is a program that runs on a computer (usually, but not necessarily, a dedicated hardware server) and handles HTTP requests from clients (usually browsers) over a network. Most web servers listen for client requests on the hosting hardware's port 80 (this is the well known port for web servers) although web servers are not limited to using port 80. We will talk more about web servers and clients late in the class.

JAVA And Its Write Once, Run Anywhere Philosophy
Now that we have discussed some of the software and networking technologies that significantly influenced the design of the Java platform we can turn to discussing some of the details of the platform itself.
How Can Java Programs Run 'Anywhere'?
Java is designed to run on a virtual machine and anything that can host a Java Virtual Machine (JVM) can run Java programs. The JVM is actually a specification and anything that implements the JVM specification can run Java programs. Currently most JVMs are implemented in software but there is also a quickly growing number of chips becoming available that implement a JVM in hardware and these chips run Java code (bytecode) natively (perhaps these chips should be called Java Actual Machines?). The following is a list of systems/things that are currently hosting Java Virtual Machines:
Operating Systems: Windows (all versions), Solaris, Linux, BE, FreeBSD, Mac, AS400, SCO Unix, Novell, IBM370, HP-UX, etc. (this list would be easier to compose if we were listing systems that did not host Java Virtual Machines!).
Web Browsers: Netscape, Hotjava, IE explorer, etc.
Embedded Real Time Operating Systems (RTOS): Wind River, Chours, QNX, etc. (almost all major real time operating systems).
PDA's like the 3COM PalmPilot.
iButtons: http://www.ibutton.com/store/index.html
Smartcards: http://java.sun.com/products/javacard/
Micro web servers: http://www.ibutton.com/TINI/index.html
Cell Phones: http://java.sun.com/features/1999/06/j2me.html
Cars: http://java.sun.com/features/1999/06/concept_car.html
Remote Cameras: http://java.sun.com/features/1999/10/robotics.html
TVs: http://java.sun.com/products/javatv/
Databases: Oracle http://www.oracle.com/java/, IBM, etc.
A number of companies now have chips available that are designed to execute Java programs:
http://www.arm.com/
http://www.ajile.com/
http://www.ptsc.com/
What Aspects Of Java Make It Different From Other Software Platforms?
The Java platform is designed for the internet and it is the only widely adopted platform that can make this claim.
Java uses late binding which means it is linked at run time not compile time.
Java uses garbage colletion which means discarded objects are reclaimed automatically by the JVM.
Java does not let the programmer use pointers indiscriminately.
Java programs are compiled into bytecode which is the native binary code of the Java Virtual Machine.
Java source files have .java extentions (MyProgram.java).
Compiled Java programs have .class extentions (MyProgram.class).
Java is multithreaded which means that many Java objects in an application can run concurrently.
Java is available in three versions, J2EE (Enterprise Edition) for enterprise work, J2SE (Standard Edition) for PC work and J2ME (Micro Edition) for small devices.
SUN's command line Java Software Development Kit (SDK) is available for free at http://java.sun.com/products/
There are also a number of free commercial quality Java IDEs available including the following: JBuilder Forte NetBeans Eclipse
Java Applications
A Java application is very similar to any other program (such as C++ programs or Visual Basic programs) except that a Java Virtual Machine has to be present before it can run Unlike other applications, however, a pure Java application can be moved to any other machine that has the same type of Java Virtual Machine and it will run without modifications. This means that a software developer only has to develop one version of their Java program and that program will run on a wide range of platforms without having to re-compile it (at least this is the ideal that Java strives for).
An excellent example of a commercial-quality client side application (which means it runs on a PC and not a server) written entirely in Java is the JEdit text editor: http://jedit.org/
Java Applets
A Java Applet is a Java program that runs inside a Web Browser. The browser must either have a Java Virtual Machine built into it or it must have a JVM added to it using a JVM plug-in. A good place to learn more about applets is: http://java.sun.com/applets/index.html and here is also a link to some more interesting applets. These Java applets should run inside your browser if you are using IE explorer or Netscape but keep in mind that the version of Java that comes with these two browsers is fairly old and that the platform has evolved significantly during the past few years.
Server Side Java
One of the most important and fastest growing areas of Java is server side Java. Server side Java consists of Java programs that run inside of a Web server. Just like the Java programs that run inside a Web browser are called applets, server side Java programs also have a cute name, they are called servlets.
Servlets are a direct competitor to the old CGI-BIN server side programming technologies and they have many advantages over CGI-BIN which include being faster, cross platform and multithreaded. Server side Java enjoys very wide industry support http://java.sun.com/products/servlet and servlets will run in any web server that supports the servlet architecture.
One of the more popular developments in server side Java is Java Server Pages (JSP) http://java.sun.com/products/jsp/index.html. Java Server Pages allows Java code to be embedded into an HTML document on the server. The Java code in the HTML page runs and inserts live data into the HTML page before it is served to the client (this is similar to Microsoft's Active Server Pages).
Application Servers
One of the largest areas of Java is Application Servers. An application server is a software platform which is being used to host the next generation of commercial-quality web applications. They typically are hooked to back-end databases, house their business logic in Enterprise Java Beans (EJBs) and use Java Server Pages (JSPs), applets, servlets etc. to provide the front-end client access to the application.
Java based application servers are going to play a huge roll in internet based software going forward and almost all of the large software vendors have based their most important internet software offerings on these application servers including IBM, HP, SUN, BEA, Oracle, Sybase, Apple and Macromedia.
Java Database Connectivity (JDBC)
JDBC allows a developer to write a Java database access program once and then the program can access data in any database that supports the JDBC interface: http://java.sun.com/products/jdbc/industry.html. The way JDBC works is that it implements an abstract view of a generic database and communicates with the target database through this abstracted view. The only requirement is that the database manufacturer must have a JDBC driver implemented for their database. Using JDBC a database can be accessed from a PC based application, an applet, a servlet or any other piece of Java code. http://java.sun.com/products/jdbc/
JAVA Beans (software components)
One of the most exciting areas of Java is Java beans. In the real world things are made of components (for example a bike has wheels, a seat, a steering wheel, etc.). Software components are a technology which allows a developer to assemble software applications using pre-made software components. Java Beans is Java's component technology (it is similar to Microsoft's COM based component technology). http://java.sun.com/products/javabeans/index.html
Another huge area at the cutting edge of the Java world is Enterprise Java Beans (EJB). EJB is used in n-tier e-business solutions and they are a cross-platform way of encoding business logic. http://java.sun.com/products/ejb/index.html
Java Media Framework, OpenGL And OpenAL bindings
The Java Media Framework allows Java programs to work with sounds, pictures and streaming video in a cross platform way. The JMF allows a program to easily capture audio and video input along with allowing the playing of numerous audio and video formats including Quicktime, MPEG1 and MPEG layer2 and layer3.
Another exciting area of Java is its new bindings to OpenGL (through JOOL, http://jogl.dev.java.net/ and to OpenAL (through JOAL, http://joal.dev.java.net/ . These new binding technologies are designed to allow Java to be competitive in the PC based computer gaming industry. http://javagaming.org/
UML (Unified Modeling Language)
Unified Modeling Language is a visual language that allows one to describe and design object oriented systems at a very high level of abstraction using standardized diagrams and symbols. Since Java is a pure object oriented language there are many UML tools available that are designed to work with it and that will automatically generate Java source code skeletons from the UML models.

Conclusion
The scope of Java is so wide that one informational web page can only barely touch the surface of it. If you are interested in Java the only way to learn it in depth is to obtain and read as many books and online tutorials on Java as you can, visit the top Java web sites daily, and program program program (this is really no different than learning any other sophisticated technology).
Here are links to some of the major Java web sites to get you started:
http://java.sun.com/
http://java.net/
http://java.com/
http://javaworld.com/
http://theserverside.com/
http://javalobby.org/
This is the end of lecture 1. Your next step is to complete lab 1 which can be found on the main class web page. Good Luck!

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:26:03

2


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 2 - Developing JAVA™ Programs (V1.1.4)
PDF
Purpose
Object Oriented Mind Re-wiring
Classes (blueprints that are used to create objects)
The Different Releases Of Java
Setting Up An MSDOS Environment To Run Java
Developing A Java Class And Running It
Purpose
The purpose of this document is to introduce the key concepts behind how object oriented Java programs are developed and the technologies that this development is based upon. The main goal is to provide enough depth and detail for you to grasp the fundamentals of how these technologies work together to produce running Java programs but not to examine these details in so much depth that they start to distract us from the primary goal developing and running simple programs. After you have developed and run a number of Java programs and are somewhat comfortable with how the technologies are working you will probably have a desire to dig deeper into the technology's details. There are a large number of very good Java books available that cover the same materials that are going to be presented in this document but in much more depth. Here are three books to get you started:
The Java Programming Language 3rd edition - A very complete description of the Java programming language.
Thinking in Java - This book is highly regarded in the Java community and it can be downloaded for free.
Inside the Java Virtual Machine - An excellent book on the internal workings of the JVM.

Object Oriented Mind Re-wiring
In this document I am assuming that you have little or no object oriented programming experience. In my opinion one of the most difficult things you will do in the area of programming is to make the mental switch from the procedural programming paradigm to the object oriented programming paradigm. The problem is not that object oriented programming is necessarily more difficult than procedural programming, the problem is that it is so different and one uses it in such a unique way to solve programming problems that some definite mental re-wiring is going to have to happen before you truly 'get it'. This mental re-wiring is a process that happens very slowly as you continuously write object oriented programs and dig deeper into the books in an effort to really understand what this object oriented stuff is all about.
Right from the beginning you can see that there is something very special and powerful going on but it will elude your efforts to firmly grasp it. When you do finally 'get it' it will not come all at once like a bright light going on. It is more like a dim light that you can sense glowing in the back of your mind that brightens very slowly. For each new programming problem you encounter the front part of your mind will still quickly produce a procedural plan to solve it but you will begin to notice that this glow in the back of your mind will start to present object oriented strategies (dim at first but slowly increasing in clarity) that will also solve the problem and these object oriented strategies are so interesting and compelling that over time you will find yourself paying more and more attention to these solutions and less and less attention to the procedural ones. Eventually a time will come when almost every programming problem will trigger the production of rich object oriented strategies for solving it from the now bright object oriented part of your mind almost to the point where you will wonder how the procedural techniques for solving these problems use to work.
Object oriented programming is a software design philosophy where software is modeled after the physical world. Object oriented programs are built using software objects which have attributes and behaviors. As a concrete example of this think of a typical office chair. The chair has attributes (color, number of wheels, material type) and behaviors (spin, roll, set height). A software object's attributes are held in data structures called instance variables and its behaviors are determined by code which is held in methods (methods are similar to C Functions or BASIC Subroutines). After an object is created it is used by sending it messages (calling or invoking its methods). In the case of the chair we could send it a chair.spin(3) message which would tell the chair to spin 3 times or a chair.setHeight(32) message which would tell the chair to set its height to 32 centimeters.

Classes (blueprints that are used to create objects)
All Java programs are built using Java classes. A Java class can be thought of as a blueprint that is used to construct objects and it is conceptually similar to a house blueprint. An architect works very hard to precisely define exactly how a given house should be constructed, what materials need to be used, what its various dimensions should be, etc. After the blueprint is finished it can be used to create one house or many houses because the blueprint contains the information that describes how to create a house, it is not the house itself. A Java programmer creating a Java class is very similar to an architect creating a house blueprint except that the architect uses a drafting table or a CAD system to develop blueprints while the Java programmer uses a text editor or an IDE to develop Java classes.
The first place to start when developing a Java program is with a text editor (IDEs have built-in text editors so I am including them in this category). Inside the editor, source code that will eventually be compiled into a Java class will be typed in and saved with a .java extension. After the .java file is saved to disk it is fed into a Java compiler (in our case the compiler's name is javac) and the compiler will generate a .class file which will have the same name as the .java file that was used to create it. The .class file is a binary file that is like a blueprint for creating objects of the type defined by this class file. During the executing of a Java program a number of .class files are loaded into memory by the JVM and the JVM uses these .class files to create the Java objects that together represent the running application. The following diagram shows this process graphically:

Keep in mind that we will be doing this process manually using command line tools but IDEs perform the same steps automatically. For those of you that are use to the normal edit/compile/link process used by most languages like C or VisualBasic notice that there is no link step present when developing Java programs. Java classes are linked every time they are loaded, not while they are being developed. The reason for this is that Java was designed to work in the dynamic environment of the internet and in this networked environment .class files and serialized Java objects were given the ability to fly across the net anytime, to any location they were needed and to be dynamically attached (linked) to running programs.
This is an advanced concept so perhaps an analogy would prove helpful. Imagine that a given Java application is a jumbo jet that is getting ready to fly across the Atlantic ocean from New York to London. Just before takeoff the blueprints for every part of this aircraft are brought to the tarmac and given to a small army of workers who use them to very quickly construct all of the components needed to build the aircraft. As each component is constructed it is attached to the proper place on the aircraft and in a short time the aircraft is complete and ready to go. The passengers are loaded and the jet takes off. After the plane leaves the ground the landing gear are disintegrated (garbage collected) because they are not needed during the flight and hauling them across the Atlantic ocean would just waste costly fuel. There is no need to worry, however, because the landing gear will be reconstructed using the proper blueprints (classes) just before landing in London
A few minutes after takeoff the pilot receives notification that the company who manufactured the aircraft's jet engines has just released a new model that is 15% more fuel efficient than the ones that the aircraft is currently using and that the airline is going to upgrade the aircraft's engines while the plane is in flight. The airline sends the blueprints for the new engines over the network to the plane and these are used to construct 3 of the new engines. After the new engines are constructed the 3 old engines are (one at at time) shut down, replaced with a new engine and disintegrated (garbage collected). The engine upgrade goes smoothly and the passengers are not even aware that the upgrade took place.
This flight just happens to have an important world figure on board and halfway through the flight a hostile aircraft is encountered and it orders our pilot to change his course. Instead of complying with this demand, however, our pilot pulls a set of blueprints (classes) from over the network for a 50mm machine gun turret, has 4 of these turrets constructed (instantiated) and then attached to the plane's top, bottom, nose and tail sections. A few blasts from one of these machine guns is enough to deter the hostile aircraft and it quickly moves away, eventually dropping off of the radar screen. The rest of the flight is uneventful. As the aircraft approaches London the machine gun turrets are disintegrated, a new set of landing gear are constructed (instantiated) using the landing gear blueprints and the plane safely lands. After the passengers are offloaded the whole plane is disintegrated and the blueprints that were used to create the plane are saved in a safe place.
This is a fairly good description of how object oriented Java technologies work. In the Java paradigm the whole network really is viewed as one big computer because every node is just a few hundred milliseconds away from every other node and the concept of distance just simply does not exist. The reason that Java programs link at run time instead of at development time is so they can take full advantage of the dynamic, flexible nature of the internet.

The Different Releases Of Java
In the next section you are going to set up your shell (command line) environment for developing Java programs using the command line tools provided in the SDK. Before we do this we will need to discuss the 3 major releases of Java that Sun has released since 1995. The first release of Java was 1.02. It was rough, a bit slow and it did not have a very rich runtime library but because it was embedded into the Internet Explorer and Netscape web browsers it was widely distributed. The next release of Java was 1.1 and it was much richer and robust than 1.02 was. It enabled people to start to do serious work with Java and many improvements were introduced during this release including a new event model, inner classes, lightweight GUI components, reflection, object serialization, remote method invocation (RMI), etc. There were many sub-versions of 1.1 released with the highest one being 1.1.8.
In Java 1.1 its developers learned a great deal about how a platform like Java should be designed and they incorporated these ideas in the next major release of Java which was 1.2. With this major release Java's developers had finally achieved a solid foundation upon which future versions of the Java platform could be built and to distinguish this release of Java as being distinct from the 'learning experience' versions 1.02 and 1.1.x they called it Java Platform 2 or just Java 2 for short. So when 1.2 was released it was called Java Platform 2 release 1.2. We are currently using Java 2 release 1.4.

Setting Up An MSDOS Environment To Run Java
Before you can type in, compile and run your first Java program you must properly set up the MSDOS window (also called a shell). It is very important that your shell paths are correctly configured when you are developing and running Java programs. At least 50% of all problems encountered with developing and running Java programs are caused by improperly configured path variables. Please take the time to understand what paths are used for and how they work.
Perform the following steps in order to set up a shell environment:Windows 95, 98, NT, ME, Windows 2000, and Windows XP
Here is a link to the instructions that need to be followed in order to install JDK1.4 on a Windows based system. These instructions describe how to set the paths on most of the most popular versions of the Windows operating system.
http://java.sun.com/j2se/1.4/install-windows.html#Environment
The MSDOS shell contains what are called Environment Variables. In order to see what these variables look like open up an MSDOS window and enter the word set. We will cover the CLASSPATH environment variable in a future lecture but for now make sure that this variable is empty by using the same techniques you used to set your PATH variable.
Additional Windows 95/98 Instructions if you are having problems
If you having problems getting your Windows 95/98 installation to work the following instructions might prove helpful:
The MSDOS window has some memory it sets aside for what are called Environment Variables. In order to see what these variables look like open up an MSDOS window and enter the word set. The set command shows the current contents of the environment variables. When Java programs run they add variables to this environment area and if the size of the area is too small then not all of the variables that Java wants to add to this area will fit and problems will occur. In order to avoid this type of problem do the following procedure. The MSDOS window has a memory properties setting called 'Initial Environment' and we are going to set it to its maximum available value (usually 4096). If you have an MSDOS icon on your desktop right click on it to get the properties dialog. If you already have an MSDOS window open there is an icon at the top of this window that shows a pointing finger. This is the properties icon.
The PATH environment variable in the MSDOS window provides all the paths that will be searched when a user types a program's name at the command prompt in order to run it. Each of these paths are separated by semicolons. By default the PATH variable usually contains a C:\WINDOWS path and a C:\WINDOWS\COMMAND path. Enter the word set at an MSDOS command prompt to see the current setting of the PATH environment variable. In order to run the command line tools that are present inside of the C:\jdk1.4\bin directory without having to type C:\jdk1.4\bin\ before each tool's name you will need to add the C:\jdk1.4\bin path to your PATH variable.
In order to add the C:\jdk1.4\bin path to the MSDOS PATH environment variable edit the autoexec.bat file that is present in the root directory of C: drive and add the following line to this file:
PATH = C:\jdk1.4\bin;%PATH%
Save the autoexec.bat file and then reboot your computer. After the computer reboots open up an MSDOS window and enter the set command. The C:\jdk1.4\bin path should now be listed as part of the PATH environment variable. In order to test this path try running the SwingSet2 demo program by performing the following steps:
cd c:\jdk1.4\demo\jfc\SwingSet2 enter
java -cp .\ -jar SwingSet2.jar enter
If the demo program runs then the path to the C:\jdk1.4\bin directory is set up correctly. If you have problems type set at the MSDOS command prompts again and see if the paths in the PATH environment variable look correct.
Linux
http://java.sun.com/j2se/1.4/install-linux.html

Developing A Java Class And Running It
In this section we will be typing in a Java program, compiling it and running it by performing the following steps:
Create a directory called javadev somewhere in your computer, you will be using this directory to save the Java programs that we will be developing in this class.
Use JEdit or your favorite text editor and type in the following source code: Hello.java (No Comments). Do not type the line numbers and colons that are at the beginning of each line, they are just there for reference.
Save this source code into the javadev directory and make sure to call it Hello.java starting with a capital H and having lower case letters for the rest of the name. In Java each .java source file can have only one public class in it and the name of the .java file that you save this source code into must have the exact same name as the public class it contains (with a .java extension added to it). After you are done saving this source code your javadev directory should have an Hello.java file in it.
In order to compile the Hello.java file go into the javadev directory and type the following:
javac Hello.java
If errors are printed, write down the line numbers that these errors occurred on and then go back to the editor, fix the lines in the source code that are producing the errors and then re-save the file. Keep compiling the .java file and fixing errors until all of the errors are gone. In JEdit, if you select View->Line Numbers a column of line numbers will appear which will make finding individual lines much easier.
After the file compiles with no errors look inside the javadev directory and you will see that the compiler placed a Hello.class file in there. This is the 'blueprint' that the JVM will use to create objects of type Hello.
Now that the Hello.class file has been created you can run it by typing the following inside the javadev directory:
java -cp ./ Hello
Notice that the .class extension is not typed when running a Java program.
The program should print some messages out to the display then exit back to the command prompt. In the near future we will be developing programs that will display a GUI but for these first few programs we will just be using the command line shell.
Now lets look at this program in more detail. Here is a link to a version of this program that has had comments added to it: Hello.java (With Comments). The first thing you will notice is that Java uses two forward slashes // at the beginning of a line in order to comment that line out just like C++ does. Java borrowed much of its syntax from C/C++ and C programmers will notice many parts of a Java program that look familiar. On line 8 the class Hello is defined and by convention all classes start with a capital letter. If the class name consists of multiple words put together then the first letter of each word is capitalized and all other letters are typed in lower case (for example public class HelloWorld). The open curly brace on line 9 is the beginning of the class and the close curly brace on line 90 is the end of the class. All methods and instance variables that are part of a class need to be inside the class's curly braces.
The Hello class contains one instance variable on line 15, one constructor method on line 22, three instance methods on lines 29, 38, 45 respectively and one static (or class) method on line 74. The purpose of instance variables are to give an object its unique attributes that differentiate it from other objects that are created from a given class and the purpose of the instance methods are to give each object its behaviors. All methods in an object have access to that object's instance variables and these instance variables can be manipulated by the code in these methods directly. By convention instance variable names start with a lower case letter and if the variable name consists of more than one word then the first letter of each word is capitalized.
The method on line 22 is a special method called a constructor. A constructor method is only invoked when an object is being created (usually by the new operator) and its job is to complete the construction of the object. After the object has been created its constructors are no longer used. The purpose of Hello's constructor is to initialize its object's message instance variable with a message that is passed to it when a new object of type Hello is being created (see lines 76 and 77 for examples of two Hello objects being created).
The methods on lines 29, 38 and 45 give objects created using the Hello class their behavior. The printMessage() method provides the behavior of printing the message that is present in the object's message instance variable and the sayGoodbye() method provides the behavior of printing the message 'Goodbye!'. The printHellos() method takes an integer number as a parameter and it prints out the word 'Hello' that many times. In Java all variables must first be declared before they can be used so in line 47 the variable count is declared to be an integer and its initial value is set to 0. By convention methods start with a lower case letter and if the method name consists of more than one word then the first letter of each word is capitalized.
The method on line 74 is a special method called a 'main' method and its purpose is to provide the JVM with a section of code that it can execute first when launching a Java program. The code in the main method will then construct any objects the program needs in order to run. The name of a class that has a main method in it is passed as a parameter on the command line when launching a Java program. When the JVM loads this class it specifically looks to see if it contains a main method and if it finds one it invokes it (if it does not find a main method in this class it throws an exception).
The main method for the Hello class creates two separate objects (instances) using the new operator which are then referenced by the variables h1 and h2 respectively (h1 and h2 are declared as variables of type Hello in the same way that count is declared as a variable of type int on line 47). A unique String parameter is passed to each object's constructor method and this String is used to initialize the object's state (attributes).
After the objects are created messages are sent to them by calling (invoking) their public methods in order to have them perform a behavior. This is done by 'picking an object up' by a variable that references it (lets say h1), placing a dot after this reference and then typing the name of one of the object's methods that you want to invoke.
This is the end of lecture 2. Your next step is to complete lab 2 which can be found on the main class web page. Good Luck!

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:25:29


3


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 3 - Classpaths, .jar Files and the SDK Documentation, (V1.1.4)
PDF
Purpose
Packages and .jar Files
The Java 2 Standard Runtime APIs (Application Programmer Interface)
JavaDoc Genterated Documentation
Example Program That Uses Strings And A JOptionPane Dialog Box
Classpaths
Purpose
The purpose of this document is to introduce you to Java's classpaths, .jar files and documentation standard. The concept of Java packages will also be introduced and we will start to use Java's GUI classes in an example program called CompareNums.

Packages and .jar Files
We have already discussed how the Java Virtual Machine uses classes as blueprints for creating objects and how classes are saved in .class files. Now it is time for us to look at how .class files are grouped in packages so that they can be easily found and also so that classes with the same name do not interfere with one another. To get started with this do the following steps:
Run Winzip or an equivalent utility (make sure you have Winzip in 'classic' mode).
Select the 'Open' icon.
Set the Files of type textfield to All files (*.*).
Navigate to the directory where you installed jEdit (most likely the C:\Program Files\jEdit X.X directory) and open the jedit.jar file.
After jedit.jar is loaded into Winzip widen the Name and Path columns by dragging the vertical lines that separate the column headings and then scroll through the window. You may be wondering how a .zip utility was able to open a .jar file and the answer is that a .jar file is just a .zip file which contains a manifest.mf file and has a .jar extension instead of a .zip extension. As you scroll through the window and look at the files in the Name column you will notice that this .jar file is full of .class files. If you double click on the manifest.mf file you will discover that it contains a list of all the .class files present in the .jar file. Scrolling a bit further will reveal .gif files, .xml files and .dtd files. Jar files not only contain .class files but they can contain any type of files that a Java program needs as a resource including image files, sound files, data files, etc.
As you continue to scroll up and down in this window start to focus your attention on the Path column. You will notice that the files in this .jar file are not just in a flat format, they are part of a definite directory hierarchy which is some cases is many directories deep. When .zip files are created one usually specifies a top level directory on one's hard drive that needs to be zipped up and the zip utility will archive this top level directory along with all of the directories inside this directory recursively until every subdirectory inside the top level directory have been archived. What this means is that when jEdit was being developed the same directory structure that you are looking at in this Winzip window was sitting live on some Java developer's computer somewhere and this directory structure was being used to actually develop the program.
In theory if we extracted the complete contents of this jedit.jar file into a tempory directory we should be able to run jEdit using the contents of this directory instead of using the jedit.jar file. Lets try it! Leave Winzip running and do the following:
Create a temporary directory somewhere in your computer called jtemp.
Copy the complete contents of the the jEdit X.X directory (most likely C:\Program Files\jEdit X.X) into jtemp. jtemp should now contain jedit.bat, jedit.jar and a number of subdirectories including doc, jars, macros, modes and properties.
Delete the jedit.jar file that is in jtemp.
Select Actions -> Select All in the Winzip program and then extract the whole contents of the window into jtemp. After the extraction is done the bsh, com, gnu and org directories should have been added to your jtemp directory.
Open a shell window, change to the jtemp directory and type the following command:
java -classpath ./ org.gjt.sp.jedit.jEdit
If everything went well jEdit should run just like it did when it was run from the jedit.jar file. This is very interesting because what it means is that the JVM treats a .jar file just like it was simply another directory. Go into the jtemp directory and then start to drill down into the org directory you find there. Keep digging into the subdirectories in the org directory until you start to find .class files. Flip back and forth between Winzip and the deeper levels of the org directory in jtemp until you become comfortable with the fact that they represent the same directory hierarchy. When developing a program its directory hierarchy is kept on a hard drive so that the text editor and compiler can easily access all the files in this directory hierarchy. When the program is ready to deploy the part of this directory hierarchy that contains the .class files is zipped up into a .jar file and the JVM then treats this .jar file just like it was the original development directory.
You may be wondering why the name of the class we are running in the jedit.bat file (jEdit) has a bunch of stuff tagged onto the front of it (org.git.sp.jedit). This extra stuff represents the package that the jEdit.class file belongs to. Find the jEdit.class file in the Winzip window and notice that Autosave.class, Buffer.class, EBMessage.class along with a number of other classes are also part of the org.gjt.sp.jedit package. In Java a package is a namespace mechanism that is used to group classes that are designed to work together. This group might be the classes that are used for an application (like jEdit) or they might be a group of classes that serve as an API for other classes (like the java.io package or the java.sound.sampled package do).
An API (Application Programmer Interface) consists of the exposed attributes and behaviors to a group or library of classes that provide a specific type of functionality and are used to build other Java programs. In object oriented programming only the attributes and behaviors (instance and class variables plus instance and class methods, sometimes generically called members) that need to be exposed to users (clients) of a class are made available for external use. Most of a classes' and object's internal methods and variables are hidden from clients of the class and only carefully selected attributes and behaviors are exposed for external client use. These exposed attributes and behaviors are considered to be the 'interface' that a client uses in order to access the functionality of a class or object (this concept of an API interface should not be confused with Java interfaces which are a somewhat different concept).
These exposed (API) interfaces that clients use in order to access the functionality of a class or object are considered to be a contract that the class or object will not break. Object oriented programs take this concept very seriously and the reason is that as long as a class or object honors the contract specified in its API it is free to internally change the way it achieves the contract. It is free to improve the technologies, algorithms etc. it internally uses to honor its API contracts and its clients benefit from these internal improvements without having to be recompiled themselves. The idea of contracts is part of the reason that Java has grown so amazingly fast during the past few years. This is because it fosters an extremely robust and stable programming environment which encourages large amounts of code reuse.
With thousands of programmers all over the world developing Java classes there is a high probability that class name collisions can occur and so Sun came up with an elegant and effective system to prevent these potential name collisions. Sun recommends that the internet domain name of the organization that is developing Java classes be used as the first part of the package name for all classes that are developed there. In order to reduce confusion with normal domain names they also recommend that one simply reverse the order of the domain name members when using them in package names. For example, Sun's domain name is sun.com and the Java classes that Sun develops will have their package name start with com.sun. The main exceptions to this naming convention are the java package and the javax package. Sun has reserved these package names for use with Java's standard runtime APIs and since these APIs need to be implemented by any entity which develops a Java 2 compatible platform the package names of these standard APIs are not tied to any specific organization.
In order to declare that a given class is part of a specific package a package statement must be present as the first non-comment line of code at the top of a .java file. This means that in the jEdit.class file the following line was present:
package org.git.sp.jedit;
As you saw in the javadev directory the package that a Java class is placed in also translates into it having to be placed into a directory structure that exactly reflects this package name. By convention package names are always in lower case.

The Java 2 Standard Runtime APIs (Application Programmer Interface)
Hopefully you are starting to see that the way Java organizes and finds the .class files it needs is by using a very simple and open system that works well across a number of platforms. Now that you have had a look inside a .jar file and studied the package mechanism a bit lets use this knowledge to look at Java's runtime APIs. Inside the \jdk1.4 directory there is a jre subdirectory. The jre directory holds Java's runtime environment which includes the JVM and the standard runtime APIs. The SDK uses the jre as its core and to this it adds a compiler and other command line tools that are needed to develop Java programs. The jre along with its large standard runtime API is also assumed to be present on any machine that has Java 2 standard edition installed on it. If your program makes use of the classes in the standard runtime API and you are sending your program over the internet to be run on another machine that has Java 2 installed on it then the API's .class files your program uses do not have to be sent too because they are already there in the destination machine.
Open up the jre directory which is inside the \jdk1.4 directory and you will find a bin and a lib subdirectory inside of it. The bin directory contains all of the native code that is needed in order to implement the JVM on a specific platform. In the case of Windows machines these programs take the form of .dll files. The lib directory inside the jre directory contains the jre's standard runtime classes. The bulk of these standard runtime classes are contained in the rt.jar file. Open the rt.jar file using Winzip and lets see what is inside of it.
It is often remarked upon how large and rich Java's standard runtime API is and as you look through all of the .class files that are inside of the rt.jar file you can see some evidence of this. As you can see most of the classes in the rt.jar file are in the java and javax top level packages but there are some other packages in there too. The java and javax packages contain a wide range of classes that can be used by your Java programs so you can develop these programs much quicker and easier than what would otherwise be the case. So now you know where Java's standard runtime APIs are and you have seen the large number of classes that the standard runtime makes available to Java programmers but at this point you may be wondering where the documentation for these classes is. The next section will cover the mechanism that Java uses to automatically generate the API documentation needed for Java programs and I think you will find it fascinating.

JavaDoc Genterated Documentation
As you have read all of the materials up to this point you may have started to discover that Java often has its own unique way of doing things, so why should documenting Java programs be any different? Two great advantages that the developers of Java had when they created it were that they did not have to deal with backwards compatibility issues and they also knew the web was going to be a big thing. In order to make creating documentation for Java programs as simple, easy-to-disseminate and standardized as possible it was decided that the default way to create this documentation would be to automatically generate it in html format from the Java source code itself using a utility called javadoc (the javadoc utility can be found in the \jdk1.4\bin directory). The javadoc utility scans Java source code files, looks for special tags present in the comment sections of this source code and then automatically generates easy to use and publish html based documentation from this source code. Lets look at the documentation that was generated for the classes in the standard Java runtime libraries.
The large documentation bundle that you downloaded and installed into the \jdk1.4\docs directory contains all of the javadoc generated documentation derived from the standard APIs along with other more general documentation about the SDK. The path to the general documentation is \jdk1.4\docs\index.html while the path to the generated API documentation is \jdk1.4\docs\api\index.html. If you bring up the web page for the more general documentation a link to the API specific documentation is contained in this general page under a link titled Java 2 Platform API Specification. For now lets jump right to the API specific documentation. Point your browser to the following file in your computer and open it:
\jdk1.4\docs\api\index.html
Earlier I indicated that Java documentation was easy to disseminate and here is evidence of this assertion. This is a URL to the same standard runtime API documentation that you downloaded and placed on your machine but this copy is up on the java.sun.com site:
http://java.sun.com/j2se/1.4/docs/api/index.html
The initial html page for any documentation generated by javadoc always consists of 3 frames and the documentation for the standard runtime APIs is no different. The frame in the upper left corner of the screen contains a link to all of the packages in an API. Make this upper left frame a little bigger and scroll through the packages that are present there. You will notice that the same java and javax packages that you found in the rt.jar file are present in the documentation. The frame in the lower left corner of the screen contains a listing of all of the classes in the API presented in alphabetical order and the large frame on the right side of the screen contains a short description of the purpose of each of the packages. Before you go any further read each of the package descriptions so you can start to get a feel for what kinds of useful resources are available in the standard runtime API.
Now lets look at the documentation that has been generated for a specific class. Search through the alphabetical list of classes in the lower left frame and locate the String class (as you scroll through these classes start to familiarize yourself with the classes that are available in the standard runtime API). When you find the String class click on it and the generated documentation for this class will appear in the main frame. The generated documentation for each class always takes the same form. The top of the page contains links to various parts of the whole API documentation bundle along with quick links to the major sections of the current page. The next section shows the package this class is a part of along which where the class fits into Java's class inheritance hierarchy.
Java uses a single inheritance scheme in which each class can only inherit attributes and behaviors from one parent class and at the top of this inheritance hierarchy is the Object class. The Object class contains attributes and behaviors that every Java class inherits (or extents) either directly or indirectly and if a class does not explicitly state that it inherits attributes and behaviors from a specific class then it is automatically assumed to inherit from the Object class (the Hello class we looked at in lecture 2 inherited directly from the Object class because it did not specify that it extended any other class). The documentation shows that the String class inherits from (extends) the Object class.
The next section of documentation gives a general description of the class. This section usually describes a classes' overall function and it will also sometimes give small example code fragments. Moving further down the page you will find a field (attribute) summary section, a constructor summary section and a method summary section. These are then followed by a field details section, a constructor details section and finally a method details section. Another name for class and instance variables are fields and the fields sections discuss these variables. The constructor sections discuss what constructors are available for use when objects are created using the class and the methods section discusses the exposed methods that are available for use in the class itself (static methods) and in objects created from the class (instance methods). Only methods that are available for use by other objects and classes are described in the javadoc documentation. Any methods that are marked private inside of a class are for internal use only and so there is no need to describe them in the API documentation because this documentation is only meant for programmers who will be using these classes externally (the 4 levels of member scope in Java are public, private, protected and package and these will be covered in a later lecture).
As you can see from this page of documentation, Strings in Java are objects and they can be created in a number of different ways. Here are a couple of examples:
String s1 = "Hello";
String s2 = new String("Hi there!");
After a String object has been created and referenced by a variable of type String then we can send messages to this String object (invoke its methods) in order to have it perform its various programmed-in behaviors. Lets take a look at the methods section of String's documentation page to see what kinds of behaviors that String objects can perform. The following code fragments show some of the behaviors that String objects can perform along with an English translation of what the code is doing
s1.length() - Hey String object that is referenced by String variable s1, how many characters do you consist of?
if (s1.compareTo(s2) == 0) { System.out.println("These Strings are equal"); }
If the Strings objects being referenced by String variables s1 and s2 are lexicographically equal then print the message "These Strings are equal".
s1.toUpperCase() - Hey String object that is being referenced by String variable s1, return a copy of yourself to me that has all of it characters converted to upper case letters.
if (s1.startsWith("He")) { System.out.println("The String starts with the letters He"); }
If the String object being referenced by String variable s1 starts with the letters "He" then print the message "The String starts with the letters He".
As you can see by looking at the documentation for the String class, String objects have a number of different methods that one can use for dealing with Strings. When looking through the String classes' documentation keep in mind that every class in the standard runtime API has an html based documentation page that is similar in structure to String's documentation page.

Example Program That Uses Strings And A JOptionPane Dialog Box
In the following example program we will begin to use some of the numerous classes that are in the standard runtime API. The javax.swing.JOptionPane class is a convenience class that can be used to generate dialog objects for obtaining input from the user and displaying output to the user. This program will use the JOptionPane's showInputDialog behavior to display an input dialog to the user and its showMessageDialog behavior to display the program's output to the user. Open the CompareNums1CompareNums1 program in a separate browser window and lets take a look at it.
On line 15 is what is called an import statement. The import statement is a convenience statement that saves typing for the programmer. The full name of the JOptionPane class referenced in this import statement is javax.swing.JOptionPane. Normally every place in the program that you wanted to use the JOptionPane class you would have to use its full name if you did not use an import statement. The import statement allows the programmer to only have to use the name JOptionPane to refer to this class instead of its full name. For convenience sake all of the classes in the java.lang package are automatically made available to a program so this is the only package that a program does not have to explicitly import.
Line 37 shows the use of the JOptionPane classes' static showInputDialog method. This method displays an input dialog to the user which has a text field in it. Whatever the user types into the text field will be returned to the program as a String object. On line 37 we are taking this String object and referring to it with the inputOne String variable.
On line 44 we are using a static utility method called parseInt(String) which is found in the Integer class (see the API documentation). This utility method takes a number in String form as a parameter and it returns the integer version of this number. We are taking this integer and placing it into the num1 integer variable. In Java almost everything is an object. An exception to this rule are the following data types which are called primitives:
Java Primitives
Primitive type
Size
Min value
Max value
Wrapper class
boolean
-
-
-
Boolean
char
16 bits
Unicode 0
Unicode 216-1
Character
byte
8 bits
-128
127
Byte
short
16 bits
-215
+215-1
Short
int
32 bits
-231
+231-1
Integer
long
64 bits
-263
+263-1
Long
float
32 bits
IEEE754
IEEE754
Float
double
64 bits
IEEE754
IEEE754
Double
The designers of Java decided to allow the language to use the above listed primitive variable types for the purpose of greater speed and efficient use of memory. These primitive variables work in a similar manner to standard C variables. The last column also shows what are called wrapper classes for each of the primitive variable types. Notice that the primitive types begin with a lower case letter while the wrapper classes are full Java classes which (by convention) begin with an upper case letter. The wrapper classes allow number objects to be created that permit the values that are stored in them to be manipulated in an object oriented manner.
The block of code from lines 48 to 63 uses standard if statements to determine the relationship between the two numbers. On line 57 notice the interesting use of the + operator to concatenate Strings together to form a new Strings. When Java encounters a line that is trying to add primitive variables to one or more String objects it internally converts the values in the primitive variables into Strings and concatenates them with the String object. On line 57 the String object that is the result of this concatenation is referred to by the answer String variable for later use.
On line 67 a showMessageDialog JOptionPane is displayed which contains the result of the comparison of the two numbers. Look at the html documentation for the JOptionPane object for more information on what this line is doing.
The last interesting thing in this program is on line 72. The System object is automatically loaded when the JVM is launched and it encapsulates information about the system the JVM is running on (for more information on the System class refer to the standard runtime API documentation). The static exit(int status) method of the System object shuts down the currently running JVM and thereby ends the program.

Classpaths
By this point you should be starting to see that the Java classpath is simply the path that the JVM checks in order to find all of the classes it needs in order to run a program. These classes can be in a directory hierarchy on the machine the JVM is running on, in a directory hierarchy contained within a .jar file or even in a server somewhere on the internet. There are a number of ways that one can set the classpath with the two most popular being from the command line (with the 'classpath' switch in javac.exe and the 'cp' or 'classpath' switchs in java.exe) and using the shell environment's CLASSPATH variable. If the CLASSPATH variable is not set then when one runs a class then the current directory is automatically added to the classpath. If, however, the CLASSPATH environment variable is set to something then only it is searched for classes and the current directory is ignored. The '-cp ./' switch we are using to run the programs should add the current directory to the classpath even if the CLASSPATH environment is set. One thing that may cause problems is if another class file with the same name as the class you are trying to run is reachable somewhere in your environment variable's classpath. The classpath is searched sequentially for classes and if two class files with the same name are present on the classpath then the first one that the JVM finds is the one it will try to run.
Here is where you can find the classpath help page for WIN32 that is present in the SDK documentation you downloaded:
jdk1.4/docs/tooldocs/win32/classpath.html
This document has most of the information that one would want to know about the classpath.
This concludes lecture3. Your next step is to do lab 3 which is present on the main web page.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:28:03

4


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 4 - Inheritance, GUI Components, Events and Interfaces (V1.02)
PDF
Purpose
Inheritance (extending classes)
Swing GUI Components
TestFrame1 Example Program (put some GUI components on the screen)
Java Interfaces
Java Events
TestFrame2 Example Program (Java events)
TestFrame3 Example Program (inheritance)
Purpose
The main purpose of the material up to this point in the class was to provide you with enough of a foundation in Java so that you could start to develop simple programs with it. After the general introduction to Java, we covered downloading and installing the software tools, setting paths and classpaths, fundamental object oriented concepts, .jar files, small programs and Java's API documentation standard. In the previous lecture you may have been surprised to see a JOptionPane GUI dialog box appear on the screen from a few lines of Java code executed from a shell command line but the standard runtime APIs have a huge amount of these type of GUI components available that can be accessed just as easily and over time you will get use to using them. Any of the GUI components that you saw in the SwingSet2 and Java2D demo programs can be accessed as easily as JOptionPane was and in this lecture we will be using some of them. This lecture will cover inheritance, GUI components, events and interfaces. The lecture is somewhat intense but if you can get through it and come away with a fundamental understanding of the topics it covers you will be doing very well indeed because these topics represent some of the powerful and subtle core ideas upon which Java is based.

Inheritance (extending classes)
Object technologies are subtle, rich and fascinating. They have many interesting ways for dealing with complexity and promoting software reuse through inheritance (extending classes) is one of them. Inheritance is the ability for a class to automatically obtain or inherit all of the attributes and behaviors of another class (called a parent, super or base class) using just a little bit of code. Attributes are obtained by inheriting a parent classes' fields (static and instance variables) while behaviors are obtained by inheriting a parent classes' methods. What this means is that a child class can do everything its parent can do and then usually additional functionality is added to this child class to allow it to do more than its parent can do.
Another aspect to this idea is that since a child class can do anything its parent can do it can be used any place its parent object can be used. Take a look at the inheritance hierarchy of the javax.swing.JFrame class in the standard runtime API documentation. This hierarchy indicates that JFrame is a Frame and Frame is a Window and Window is a Container and Container is a Component and finally Component is an Object (just like all the other classes are in Java since the Object class is the root class from which they all descend). A more general way to look at this is to say a child class can be used any place any of its ancestor classes can be used. This means that JFrame is a Frame and a Window and a Container and a Component and an Object. This ability of a class to be used as if it were any of its ancestors is one of the major ideas which allows the concept of polymorphism to be used in object oriented languages but we will have to save the discussion of how polymorphism works until later.
There are two types of inheritance (called single inheritance and multiple inheritance) and Java uses single inheritance. With single inheritance each class can only have one parent class although each parent class can have many children (multiple inheritance allows multiple parent classes). At the top of Java's class hierarchy is the Object class and all Java classes have the Object class as an ancestor. The Object class has attributes and behaviors that are useful for all classes and if a class does not explicitly state that it extends a given class then it automatically extends the Object class. Not only does a child class inherit all of its parent classes' behaviors but it can change the behaviors it inherits from its parent by overriding any methods it inherits from its parent. Overriding a method is accomplished by creating a method in the child class with the same name and passed-in parameters (together also called a signature) as a method inherited from its parent. When this overridden method is invoked in the child the new method is the one that is used and the old version of the method inherited from the parent is effectively hidden.
Inheritance promotes software reuse by encouraging programmers to find a pre-existing class that provides a significant amount of the functionality that they would like a new class to have, extend this class, override any behaviors that they would like to change and add the additional attributes and behaviors to the class that it needs. As you have seen there are a large number of classes in Java's standard runtime API that can be extended along with countless classes available on the internet. Inheritance can run many levels deep and a look through the standard runtime API documentation will give you a good indication how this ability can be used to great advantage. We will begin our study on how inheritance is used in Java by looking at some of the GUI components that come in the standard runtime API in the next section.

Swing GUI Components
Java makes use of two different kinds of GUI components called heavyweight components and lightweight components. Heavyweight GUI components make use of the GUI components that are already available on the system that Java is implemented on and they simply wrap this native GUI component with a Java object. Lightweight GUI components have all of the code needed to create the component written in Java. Heavyweight GUI components are easier to implement than lightweight GUI components and heavyweight components were the only type of components that were available in the earlier versions of Java (these heavyweight components are present in the java.AWT package and they are still available for use in the current version of Java).
The drawback to using heavyweight GUI components is that native GUI components look and act differently across multiple platforms. This means that only the common denominator GUI functionality which was present on most platforms could be used by earlier versions of Java and the same Java program running on multiple platforms would not look or act the same. In order to fix this problem the rich, powerful and flexible 'Swing' lightweight Java GUI components were developed and this is the preferred GUI component set for building user interfaces in Java (the SwingSet2 program was designed to demonstrate what Swing components looked and acted like).
Before we look at our first Swing based program we have to discuss yet another unique feature in Java. In languages like VisualBasic the preferred method for sizing and placing GUI components on the screen is to use absolute pixel coordinates and sizes and this method works well when you know what operating system the program will be running on and what fonts will be available. If you do not know what operating system your program will be running on or what fonts will be available, relying on absolute pixel coordinates and sizes to place and size your GUI components does not work. Even small font or windowing system variations between systems will cause problems like button labels overwriting the bounds of their buttons or GUI components overlapping one another.
How does Java overcome this limitation? It uses a technique which involves placing the GUI components into containers and these containers use layout managers to automatically adjust the placement of components while the program is running on the target system. Swing containers are also GUI components so they can be placed into other containers and the combination of nested containers each utilizing various layout managers allows almost any desired GUI layout to be achieved. For those of you use to laying out GUI components with an absolute pixel coordinate system, using layout managers will be a bit of a change but this technique needs to be used if you want your programs to be able to run on multiple platforms.
The Java 2 platform comes with the following layout managers: BorderLayout, BoxLayout, FlowLayout, GridLayout and GridBagLayout. Very briefly BorderLayout divides a container into a north, south, east, west and center cells and GUI components or other containers can be placed into any or all of these cells. BoxLayout allows GUI components or other containers to be sequentially placed into a container either vertically or horizontally. FlowLayout places GUI components or other containers into a container from left to right and it will wrap these components to the next 'line' below the current one if the components run past the right side of the container. GridLayout places GUI components and other containers in a grid and GridBagLayout is not easy to explain so I will let you look it up in the API documentation. If you would like to see some more information on layout managers you can take a look at this layout manager tutorial page on the java.sun.com site.

TestFrame1 Example Program (put some GUI components on the screen)
Lets take a look at a small Swing based GUI program called TestFrame1.java (the source code for this program along with the source code for the other two TestFrame programs we will be looking at in this lecture are in this TestFrame.zip file. The program consists of a JFrame (which defaults to BorderLayout mode) a Box (component container), a JTextField, and two JButtons. Instead of being directly placed inside the JFrame the GUI components are first placed into a Box object (container) called guiBox. The container guiBox uses a BoxLayout manager which (in this case) is set to vertical layout mode to position the components placed into it and this means that the GUI components will be placed into the container sequentially from top to bottom in the order that they were added to the container. After the GUI components are placed into the guiBox container guiBox itself is then placed into the North cell of the JFrame. Compile and run this program so you can see what it does and then we will look at some of its more interesting features.
TestFrame1 demonstrates how to create a class that will show a JFrame which contains a text field along with a couple of buttons. The class inherits most of the functionality it needs by extending javax.swing.JFrame. In this class the buttons are not programmed to do anything. The import statements starting on line 12 save programmers from having to type the fully qualified names of the classes they are using from the standard runtime API or other APIs. Notice that some classes are listed specifically while others are made accessible as a group using the wildcard character '*' and either way is acceptable. On line 21 the extends keyword is used to indicate that this class uses the JFrame class as a parent and that it inherits all of JFrame's attributes and behaviors. On line 35 the first line of the constructor calls the parent classes' constructor in order to allow the parent's constructor to finish its part of the object's construction. After the parent classes' constructor is done constructing the part of the object it is responsible for TestFrame1's constructor can then finish the object's construction. Whenever a constructor is going to call its parent's constructor this constructor invocation must be the first line of code it executes.
On line 41 a Box object is instantiated which will be used as a container to put the GUI components into. Box objects use the BoxLayout LayoutManager which gives us the option to flow objects placed within it either vertically or horizontally. We have chosen to flow the components vertically. On lines 44-45 a JTextField object is instantiated and added to guiBox. while on lines 49-51 a JButton object is instantiated, its background color is set to green and it is then also added to guiBox. The code on line 50 is a good example of setting the state of an object. Objects instantiated using the JButton class have an instance variable which holds the background color (or attribute) of the button. These objects also have a setBackground method which allows this attribute to be easily changed. The code on lines 55-57 creates a second button and it is very similar to the code used to create the first button.
JFrames represent a special type of container called a top level container. Top level containers behave similarly to regular containers but the way that GUI components and other containers are added to them is slightly different. On lines 61-62 you can see that instead of directly adding GUI components and other containers to the JFrame we first have to ask the JFrame for a reference to the internal container it uses for this purpose and then we can add GUI components and other containers to this container. Since we have already added the JTextField and the two JButtons to guiBox our last step is to add guiBox to the JFrame's container. This container defaults to BorderLayout which means that it has a north cell, a south cell, an east cell, a west cell and a center cell. On line 62 you can see that we add guiBox to the container's north cell.
At this point we are not going to explain the section of code from lines 68-75 in depth but its purpose is to shut the JVM down when the go-away icon is selected (in the upper right hand corner of the frame) or File-> Close is selected (instead of the word File this frame displays an icon of a steaming coffee cup). On line 79 the frame's pack method is invoked and this method causes the container to re-layout its components (this is often done after new components have been added to a container). On line 82 the frame's size is set and on line 85 a message is sent to the frame which tells it to show itself on the display. When you run this program you will see that text can be typed into the text field and that both of the buttons can be pressed but that pressing the buttons does not do anything useful. Java uses events to allow objects notify other interested objects that some event like a button press has occurred. In TestFrame1 we would like to have both button1 and button2 notify another object that their respective buttons have been pressed and then this listening object can perform some desired behavior like displaying a unique message in the text field for each button. The next program (TestFrame2) will demonstrate how events are used to hook GUI components together but first we must discuss the concept of Java interfaces.

Java Interfaces
What Java loses by only allowing single inheritance instead of multiple inheritance it mostly gains back by using interfaces. The concept of interfaces is very powerful and this power is heavily leveraged throughout Java. Even though the concept of interfaces is powerful it is so simple and subtle that most people do not immediately see how it is used. An interface is nothing more than a list of unimplemented public methods (we will discuss the public keyword in a later lecture). When a class indicates that it implements a given interface it is actually entering into a contract which states that it will add the methods listed in the interface to itself. A class is free to implement as many interfaces as it needs to. See, I told you interfaces were easy! Are we ready to move on to the next section now? No? You don't quite get it yet? Hmmm, ok, I also said that interfaces were subtle so lets explore them in a bit more depth.
One of the main pillars that provides Java with a substantial amount of the power it is able to wield is its heavy use of API interfaces and contracts. When I talk about API interfaces and contracts I am talking about interfaces in a general sense and when I talk about Java interfaces I am referring to a specific mechanism built into the Java language which is used to attach a pre-defined interface to a class. When I refer to Java interfaces (the mechanism) I will print the word interface in bold. Java's APIs are all about interfaces and contracts because they consist of attributes and behaviors that a set of classes state that they will provide, not the implementations of those classes. As long as a class faithfully provides the attributes and behaviors that it states it will in its published API one does not need to be concerned with the details of how it is providing this functionality. In order to give you a feel for how the concept of API interfaces and contracts (again used generally) work perhaps a couple of analogies will prove useful.
For the first analogy lets use the automatic transmission car as an example. If you think about it almost all of the details about how a car actually works have been hidden from the driver (user or client) and the only thing they have to deal with is an AutomaticCarOperator interface. This AutomaticCarOperator interface consists of a steering wheel, an accelerator pedal, a break pedal and a transmission selection lever which has Park, Drive and Neutral positions on it (most transmissions also have the ability to force the selection of lower gear ranges like L1 and L2 but we will ignore these for this discussion). For the most part this AutomaticCarOperator interface is all a person needs to know in order to operate an automatic car and a knowledge of this interface will give this person the ability to operate any car in the world. The interesting thing is that interfaces are more durable (and almost more real) than their implementations. This can be illustrated by imagining a person who was put into hibernation in the 1950s and woken up today. The AutomaticCarOperator interface in use today is identical to the one used to operate 1950's automatic transmission cars and so this person would have no problem operating a modern car even though the details of how this AutomaticCarOperator interface are implemented have radically changed since the 1950s.
The typical automatic car in the 1950s had a carbureted engine, rear wheel drive, drum brakes, and a hydraulically shifted transmission. The typical modern car has a fuel-injected engine, front wheel drive, disc breaks and an electronically shifted transmission. A 1950s mechanic that had been placed in hibernation and woken up today would have to be completely retrained before he could work on a modern automobile. This might be a good place to point out that one of the reasons Java imposes a strict object oriented paradigm and religiously enforces the concept of interfaces and contracts is to allow the details of how an API is implemented to change and improve. In languages like C++ the concept of interfaces and contracts is difficult to enforce because all code has unlimited access to all the other code that it is running with which translates into this code having direct access to the implementations of the other code's interfaces. In terms of our automatic car analogy this would mean that some car operators in the 1950s might get use to having direct access to the hydraulics that shifted their transmission to the point where they forgot how to shift the transmission using the AutomaticCarOperator interface. When an interface-breaking hibernating operator like this is woken up today and they try to drive a modern electronically shifted automobile by sticking their hand into the transmission in order to find the purely hydraulic shifting components they are use to using they will be unable to operate the car because these hydraulic shifting components have been replaced by electronic shifting components.
The concept of API interfaces and contracts as described above would be enough of a justification for Java to heavily leverage it but as is usually the case with subtle things there is much more here than meets the eye. Now that you have a fundamental idea of how interfaces and contracts can be useful lets kick the concept into hyperdrive and see some of the other things it is capable of. In the physical world there are many things that move around in a primarily two dimensional plane. A partial list of these things include cars, trucks, buses, boats, motorcycles, hovercraft, snowmobiles, horses, turtles, cats, dogs, etc. In theory if a person knew how to use the AutomaticCarOperator interface and if they needed to use a motorcycle but they had never ridden one before, the concept of interfaces and contracts could help them out. If the motorcycle implemented the AutomaticCarOperator interface then when the person looked at the motorcycle all they would see was the AutomaticCarOperator interface. They would get 'into' the car, put it in drive, press the accelerator pedal and drive away and the person would have no idea that they were actually riding a motorcycle. This concept can even be extended to something like a horse. If a given horse implemented the AutomaticCarOperator interface then when a person who knew this interface but did not know how to ride a horse looked at the horse all they would see is the AutomaticCarOperator interface and they could use this interface to 'operate' the horse. Any of the things in the above list could be made to implement the AutomaticCarOperator interface and then it could be used by a person who only knew the AutomaticCarOperator interface to 'drive' it around. If you think this idea is fantastic wait until you see all of the amazing ways that Java uses this concept. It will absolutely blow your mind!
A second analogy which might help to explain the concept of interfaces deals with Legos and Tinker Toys. Legos have an interface which consists of a series of 4.75mm diameter raised cylinders built into one side of a plastic block which fit snugly into receptacles present in another block. This is the main interface that one uses to build things using Legos. Tinker Toys have an interface which consists of 9.5mm diameter holes drilled into the side of a block and into which cylindrical pipes or sticks snugly fit. Many interesting things can be built with Legos and many interesting things can be built with Tinker Toys but Legos and Tinker Toys can not be easily used together to build things because their interfaces are not compatible. How can we solve this problem? How about making a Lego block 'implement' the Tinker Toy interface by putting a 9.5mm diameter drill bit into a drill and drilling a 9.5mm diameter hole into the side of a Lego block? Now that this Lego block 'implements' the Tinker Toy interface we can stick a Tinker Toy stick into it and start to use these two systems together to build things.
Once one knows how to easily implement the Tinker Toy interface a whole new world of interesting possibilities presents itself! Did you ever want to use Tinker Toys with your car? Having your car implement the Tinker Toy interface is as easy as drilling 9.5mm diameter holes into it. Now you can add Tinker Toy based creations to your car that are much more interesting to look at than a new paint job! I will spare you further descriptions of all the things in the world that could benefit from implementing the Tinker Toy interface but hopefully you are beginning to see how this idea works. The important concept to grasp here is that the Tinker Toy that is stuck into any thing that 'implements' the Tinker Toy interface has no idea of what it is really attached to. From this Tinker Toy's point of view it is simply stuck into another Tinker Toy and it treats it as such.
As stated earlier, a Java interface (the mechanism) is nothing more than a list of unimplemented methods. When a class indicates that it implements a given interface it is actually entering into a contract which states that it will add the methods listed in the interface to itself. A class is free to implement as many interfaces as it needs to. The reason that you would want classA to implement a given interface is that you want classB's objects that are designed to work with this interface to be able to work with classA's objects. Even if classA was a very rich class with a many interesting attributes and behaviors, when classB's objects 'look' at classA's objects the only thing they see is the interface and so to classB's objects classA's objects represent just the contract specified in the interface and nothing more. This concept will become clearer when we study Java events in the next section.

Java Events
If you are starting to grasp how interfaces work then understanding Java's event mechanism will be a breeze. For those people who are use to using events in other environments (such as VisualBasic or the Macintosh) Java events are going to appear quite strange. The reason for this is that instead of being hidden and working 'behind the scenes' Java's event mechanism is to a large extent built on top of the language itself and so the operation of this mechanism is open to the programmer to observe and to extend in order to build new events. Just like Java interfaces, Java events are simple, powerful and subtle and here is how they work. A Java object sends an event to another (listening) object by invoking a method in that second object and passing to this method an event object (which encapsulates details about the event) as a parameter. That's it, see how easy it is? And you thought Java events were going to be esoteric and mysterious!
At this point., however, you might say 'wait a second, how does the object which is sending the event know what method to invoke in the second listening object in order to notify it that the event occurred?'. In order to solve this problem what we need is a mechanism that would force any object that wanted to be notified when a specific type of event occurred to always have a specific pre-defined method in it so that the object sending the event could invoke this method in order to notify this second listening object that the event happened. The object sending the event does not care what other attributes and behaviors the listening object has as long as it implements the special pre-defined method that knows how to handle that specific type of event. The only thing the object sending the event sees when it looks at the object listening for events of that type is a method or methods which know how to handle these type of event messages. If you are thinking that this sounds like a problem that is begging to be solved by an interface then you are correct.
Any Java class that wants its objects to handle event messages of a specific type must implement a pre-defined listener interface that specifies methods that are designed to work with objects that will be sending these type of events. After implementing an interface that is designed to work with a specific event type, the listener object registers itself with an object that produces these type of events. When the event occurs in the producing object it notifies all of the objects that have registered with that producer as event listeners (for that type of event) by invoking the special method or methods present in these listening objects that were specified in the interface they implemented for that event type. Java events are explored in the TestFrame2 program (discussed below) and hopefully when you see them in use they will be easier to understand.

TestFrame2 Example Program (Java events)
Lets take a look at a more complete version of the TestFrame1 program given above called TestFrame2 that uses ActionEvents generated by the two JButtons in order to have each button print a message unique to that button in the JTextField. TestFrame2 has all of the attributes and behaviors that TestFrame1 does except that it has events implemented in it. Instead of using inheritance to give TestFrame2 the attributes and behaviors already present in TestFrame1 we use the traditional technique of copying and pasting the sections of source code we want from TestFrame1 to TestFrame2. The final version of this program (called TestFrame3) will then use inheritance to extend TestFrame2 and then add some attributes and behaviors to it so you can see how this code reuse technique is superior to the source code copy and paste technique.
On line 18 of TestFrame2 the class declaration indicates that it implements the ActionListener interface by using the implements keyword. Find the ActionListener interface in the SDK standard runtime API documentation and look at it. The documentation for this interface is listed in alphabetical order along with the classes that are present in the frame in the lower left corner of the main documentation window (notice that interface names are shown in italics). The ActionListener interface specifies that any class that implements this interface needs to have a public void actionPerformed(ActionEvent e) method in it. Since TestFrame2 implements the ActionListener interface it MUST have this method in it somewhere and sure enough there it is starting on line 104.
The fact that TestFrame2 implements the ActionListener interface should tell you that objects that are instantiated from this class will be designed to listen for Action events coming from another object. Which objects are going to be generating these Action events? How about the two JButtons? On lines 55 and 61 you can see that our frame object is registering itself as a listener of Action events with the two JButtons and when either of these two JButtons is pressed they will wrap this event occurrence in a new ActionEvent object and send it as a parameter to the frame's actionPerformed method when they invoke it to notify the frame object that the event occurred . Compile and run TestFrame2, press both of its buttons and see the unique message that each one displays.
Lets go back to line 104 to see what happens when one of the JButtons invokes the JFrame object's actionPerformed method. The first thing that happens is that the ActionEvent object that a JButton sent us is queried to see which object was the source of this event. The ActionEvent object's getSource method returns the reference of the object that sent the event on line 106. This object reference is compared with the reference for button1 and the reference for button2 and whichever button was the source of the event will have a method called which is designed to deal with events originating from that button (we could have handled each button's events inside the if statement but it is clearer and more flexible to have an event handler method built into the receiving object that can be invoked to handle events originating from a given source). The event handler method for button1 starts on line 121 and the event handler method for button2 starts on line 127. The event handling code in both of these two methods simply sends a message to the object referenced bymessageTextField telling it to display a certain String.

TestFrame3 Example Program (inheritance)
We will conclude this lecture by looking at program called TestFrame3 which demonstrates how inheritance is used in Java. In order to run this program make sure that it is in the same directory as TestFrame2 and that TestFrame2 has already been compiled. TestFrame3 inherits all of TestFrame2's attributes and behaviors and to these it adds a third button that prints its own unique message in the JTextField and changes its background color when pressed. On line 14 you will notice that TestFrame3 states that it extends TestFrame2 by using the extends keyword. A quick look through TestFrame3's source code will show you that the only code that is present is code that is either adding new attributes and behaviors to what was inherited from TestFrame2 or changing (overriding) behaviors that were inherited from TestFrame2. This technique of code reuse is really much cleaner than source code copy and paste.
On line 16 a JButton instance variable is being added for the third button and on lines 27-30 this third button is being instantiated, initialized and added to guiBox. You may notice that on line 28 a Color object is being instantiated in order to set button3's background color. Color objects allow us to select a color using the color's RGB (Red, Green and Blue) values and this give us access to a wider ranges of colors than the color constants that button1 and button2 used (are you starting to see that practically everything in Java is an object?). Line 29 shows that the JFrame object is registering itself as a listener to button3's Action events just like it did with button1 and button2.
On line 41 TestFrame3 overrides the actionPerformed method that it inherited from TestFrame2 in order to change its behavior to include checking for events coming from button3. Starting on line 61 an event handler method is added to handle events coming from button3 and finally on lines 66 and 67 behavior is added to this event handler which allows it to change button3's background color. Notice how easy it is to reach into the standard runtime APIs and grab classes that provide rich and useful attributes and behaviors. The standard runtime API is stuffed full of classes like this.
This concludes lecture 4. It was an intense ride but I hope you enjoyed it! Your next step is to do lab 4 which can be found on the main page of the class web site.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:26:53

5


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 5 - Adapters, Anonymous Inner Classes, Graphics and Legacy Collections (V1.01)
PDF
Purpose
The WindowListener Interface
Abstract Classes, Adapters And Anonymous Inner Classes
Java Graphics
The Vector And Enumeration Legacy Collections
The GraphicsDemo2 Class
Purpose
In this lecture we will be covering a fairly wide range of topics but these topics fit together and you will need them in order to do any serious work in Java. I know it has been an intense ride so far but in my opinion learning this information is a worthwhile investment of your time and energies and one way or another you will be paid back with interest for your efforts.

The WindowListener Interface
In an earlier lecture I promised you that we would take a closer look at the code that was being used to handle events coming from a JFrame's go-away box and that is what this section will cover. Bring up the TestFrame2 program in a separate browser window and take a look at lines 73-80. The addWindowListener method invocation on line 73 should look somewhat familiar to you because it is similar to the addActionListener method invocations on lines 55 and 61. As you recall the addActionListener method is designed to take an object which implements the ActionListener interface as a parameter and add it to a list of objects to get notified of actions occurring to the component. In TestFrame2 the frame implements the ActionListener interface and then registers itself as a listener for button presses occurring on the two JButtons. In a similar manner the addWindowListener method is designed to take an object which implements the WindowListener interface and add it to a list of objects that will get notified when WindowEvents are occurring in the target object. "Ok", you say, "I am starting to understand how interfaces and events work now but I do not see where WindowListener is getting implemented in TestFrame2. Which object is implementing the WindowListener interface?". This is a fair question but it is going to take a bit of work to explain.
Find the WindowListener interface in the SDK API documentation and look at the 7 methods it specifies. These methods handle most of the actions that might occur on a frame (such as windowIconified, windowDeiconified, windowClosing, etc.) and any class that implements the WindowListener interface must implement these 7 methods. The TestFrame4 class is a version of TestFrame2 but instead of using an adaptor and an inner class (which we will get to shortly) to handle window events it implements the WindowListener interface directly. Bring up TestFrame4 in a separate browser window and look at it. On line 17 notice that a class can implement as many interfaces as it needs to. TestFrame4 implements the one actionPerformed method specified in the ActionListener interface on line 69 and it implements the 7 methods specified in the WindowListener interface on lines 101-124. Line 59 shows TestFrame4 adding itself as a listener for its own window events and this is perfectly acceptable as long as it implements the correct interface (which it does). Compile and run this program (it is in this testframe.zip file that you downloaded in lecture 4) and you will see that it will shut down the JVM when the frame's go-away box is pressed just like TestFrame2 did. Just for fun TestFrame4 also adds behaviors to the windowIconified and windowDeiconified methods that prints a message to System.out when these two events occur (try iconifying and deiconifying the frame to see what this does).
The way that TestFrame4 handles window events is easier to understand than the way TestFrame2 handles them so you might be wondering why we bothered with the way used in TestFrame2 at all. One good reason is that it takes a programmer less time to type in the code used in TestFrame2 then it takes them to type in the code used in TestFrame4 (it took about 2 minutes for me to type in TestFrame2's window event handler and about 8 minutes to type in TestFrame4's handler.). Another good reason is that in TestFrame4 all 7 methods specified in the WindowListener interface need to be implemented in the program even though only a few of these methods are actually being used. In TestFrame2 only the methods that are being used need to be typed in. Have I given you enough of an incentive to learn the techniques that TestFrame2 uses to handle window events yet? I hope you said 'yes' because this technique is covered in the next section.

Abstract Classes, Adapters And Anonymous Inner Classes
An abstract class is a class that has some of its methods implemented and some of its methods defined as only method signatures with no implementations. Abstract classes are used in cases where it makes sense to have a child class inherit a mix of implemented and unimplemented methods from a parent. The unimplemented methods are usually specialized and they are best inherited as just method signatures which the child will then provide the specialized implementations for. Abstract classes are designed specifically to only be used as parent classes that other classes can extend and they can not be used to directly instantiate objects.
We have already talked about how it can sometimes be a pain for a programmer to have to implement all of the methods in a given interface even if only a few of them are actually going to be used. Perhaps you are wondering if the concept of abstract classes can be used to help us out with this problem and if so you are correct. In Java an adapter is a class that extends an abstract class which implements a given interface and it is used as a convenience class for other classes that you do not want to implement this interface in (because it is a pain and the extra unused code clutters up the class you are working on). TestFrame5 is yet another version of TestFrame2 and it uses a WindowAdapter and an inner class to handle window events. On line 100 a special type of class is defined called an inner class and this class has been given the name HandleWindowEvents . This class is called an inner class because it is a class defined inside of another class. An object instantiated from an inner class has access to all of the fields and methods of the class it is defined in and the formal name for a class which contains another class is an outer class . This inner class extends the WindowAdapter class and it only overrides those methods for which it needs to implement behaviors. Take a look at the API documentation for the WindowAdapter class to see what it contains.
On line 56 an object of type HandleWindowEvents is being instantiated and then registered with the frame as a listener to its window events. Compile and run TestFrame5 and then notice on line 109 that since the HandleWindowEvents class was defined inside TestFrame5 it has access to TestFrame5's members and so it can reference the JTextField which is defined in TestFrame5 in order to print a message. All class definitions must generate class files and if you look inside the directory you compiled TestFrame5 in you will notice a .class file called TestFrame5$HandleWindowEvents.class. All inner class definitions generate .class files that look similar to this on and you can see that the name of the inner class is present along with the name of the class it was defined in and these names are separated by a $.
We are now at the point where we can finally tackle the original window event handling code present in TestFrame2. On line 73 of TestFrame2 the (hopefully) now familiar addWindowListener method is expecting to be passed an object that implements the WindowListener interface as a parameter. Something subtle and interesting happens on line 74 in that a new WindowAdapter object is instantiated using the new keyword but notice the open curly braces on lines 74 and 79 which enclose a windowClosing method. What is happening here is that an anonymous class that extends the WindowAdapter class is being defined on-the-fly and in this definition it is only overriding and implementing the windowClosing method which it inherited from WindowAdapter because this is the only behavior that we are interested in using. If you look inside the directory where TestFrame2 was compiled you will see a .class file called TestFrame2$1.class which was generated by this anonymous inner class. Anonymous inner classes are used fairly regularly throughout Java because they are easy to use, quick to type in and they hide code that is not really being used for anything important in a given class. These classes are called 'anonymous' because the programmer does not explicitly give them a name.

Java Graphics
Graphics is another area where Java tends to do things differently than what you may be use to. Java objects that are designed to be displayed on a graphics screen 'know' how to draw themselves because these drawing behaviors have been built into them. In the next few sections we will be looking at 3 classes that will demonstrate some simple Java graphics. I have placed these 3 programs into a package called graphicsdemo so you can get some experience working with packages. Download this graphicsdemo.zip file and unzip it in a workdirectory. You will notice that since these 3 programs are part of the graphicsdemo package they are placed into a directory called graphicsdemo. In order to compile and run these classes your current directory must be set to the directory which contains this graphicsdemo directory. In order to run the first program set your current directory to the directory that holds the graphicsdemo directory and type the following:
javac graphicsdemo\GraphicsDemo1.java
java graphicsdemo.GraphicsDemo1
Notice that when you compile the GraphicsDemo1 program you must give the path to it to the compiler and when you run it you need to use its fully qualified name (which includes the package prefix and the class name). Before we look at GraphicsDemo1 itself lets look at the DrawGraphics class which it uses. If you look inside the graphicsdemo directory you will notice that .class files were generated for GraphicsDemo1 itself, the inner class GraphicsDemo1 uses to handle the go-away box event and also for DrawGraphics. When a .java file is compiled if it uses other classes, and these other classes are not compiled yet, the compiler will go ahead and compile them automatically.
On line 7 of DrawGraphics the package command is used to indicate that this class is part of the graphicsdemo package. Line 12 shows that this class extends JPanel so it inherits all of JPanel's attributes and behaviors. A look at the API documentation for JPanel shows that one of its ancestors is a Component and one of the many methods that it inherits indirectly from Component is the paint method. All components are able to paint themselves using this method and any class that wants to control how it is painted must override the paint method it inherits and add code to this method that draws what the component needs to show. The paint method is passed a Graphics object which is an object that knows how to draw things on itself like lines, rectangles, circles, etc. In order to have it draw what the component should look like you simply send it messages which tell it what you want it to draw.
DrawGraphics' paint method begins on line 33. The block of code starting on line 36 clears the drawing area and the code on line 40 draws a black line around this drawing area. Line 43 tells the graphics object to set its drawing color to blue and then line 44 tells it to draw a line (if you want to know what the parameters which are being passed to the drawLine method are doing look the Graphics class up in the standard runtime API documentation). The blocks of code starting on lines 47, 51 and 55 are being used to draw a rectangle, a circle and the word 'Hello'. The fillOval method on line 52 is using the circleCenter instance variable from line 15 in order to determine the position of the circle. The reason we are doing this is so that the scrambleCircle method starting on line 61 can randomly generate a new position for this circle when this method is called. The DrawGraphics class does not have a main method because it is not designed to be run directly but instead it is designed to be used only by other classes. Now that we have looked at the DrawGraphics class we can move on to the GraphicsDemo1 class.
Open GraphicsDemo1 in a browser and lets take a look at it. On line 8 GraphicsDemo1 has a package command that identifies it as being part of the graphicsdemo package just like DrawGraphics is. On lines 41 and 42 a DrawGraphics object is instantiated and added to another JPanel called graphicsContainer and this container is then added to the frame on line 46. When GraphicsDemo1 is executed it displays a 75 pixel by 75 pixel panel and on this panel are drawn a line, a rectangle, a circle and the word 'hello'. The GraphicsDemo2 class which we will cover momentarily contains a bit more interesting behavior than GraphicsDemo1 does but before we look at this class we will first need to discuss Java's Vector and Enumeration classes which are covered in the next section.

The Vector And Enumeration Legacy Collections
Java2's standard runtime APIs contain a number of very power interfaces and classes which are used for holding and organizing groups or collections of objects and together these are known as the collections framework. In this class we are not going to study the collections framework in depth but if you are interested in doing this on your own (which I highly recommend) then bring up the /jdk1.4/docs/guide/collections/index.html file which is part of the SDK's documentation bundle and take a look at it. For now we are only going to study two legacy collection classes called Vector and Enumeration. The two main reasons that we are going to be covering these two collection classes is that they are very widely used (so you will almost certainly encounter them eventually) and many of the smaller devices that Java runs on only support the legacy collections. The nice thing is that Vector and Enumeration work in a similar manner to the new collection classes and so after you become comfortable with how they are used this understanding will help you when you begin exploring the full collections framework.
Vector objects can be thought of as smart arrays or smart containers which can store object references. Objects can be added to a Vector using Vector's add method and they can be removed from a Vector using Vector's remove method. A Vector will dynamically grow to accommodate the number of objects it is asked to store. It can tell you how many objects it is currently storing, give you the first object in its list, the last object in its list or any object in between if you provide an index for it. As you can imagine Vectors are very useful objects and one very quickly gets use to using them instead of using arrays. The interesting thing about the collection classes is that they can hold objects of different types in the same collection. This means that you could create a Vector object and then have this Vector hold a mix of String objects, JButton objects, JTextField objects etc. without any problems.
The reason that the collection classes are able to do this is that they use generic Object references internally in order to reference the objects that they are holding. In object oriented programming a classes' reference type can also be used to reference any of its direct or indirect children. For instance, in an earlier lecture we indicated that JFrame is a Frame and Frame is a Window and Window is a Container and Container is a Component and finally Component is an Object. This means that a reference of type Component could be used to refer to a JFrame object but only the attributes and behaviors that JFrame inherited indirectly from Component would be accessible using this reference. This subject is also tied to the concept of polymorphism but we will save this discussion for a later lecture. We can take JFrame's ancestry all the way back to the Object object and since all objects in Java's object hierarchy directly or indirectly inherit from Object, references of type Object can be used to refer to any object type.
Enumeration objects are much simpler than Vector objects and they serve a specific purpose. Enumeration objects are like a bag full of candy. Every time you take a piece of candy out of the bag and eat it the bag gets lighter and emptier and eventually all of the candy is gone and the bag is completely empty. In a similar manner Enumeration objects start will a full 'bag' of objects references but as they are removed the Enumeration object becomes emptier and eventually it will be completely empty. Enumerations are usually used as object oriented substitutes for looping through arrays and again once you get use to them you will not want to loop through arrays if you can reasonably avoid it. Enumerations need to obtain their initial and subsequent 'bag' of object references from a more permanent source but that is ok because Vectors are designed to give you a complete copy of all the object references they contain, encapsulated in an Enumeration object, if you ask them to.

The GraphicsDemo2 Class
Lets see how the GraphicsDemo2 class uses a Vector and Enumerations to implement some interesting behaviors. GraphicsDemo2 displays 8 DrawGraphics objects and then it continuously cycles through these objects and has each one randomly reposition its circle. A Vector instance variable is created on line 30 and it will hold a reference to each of the 8 DrawGraphics objects that are being displayed in the frame. On lines 43-49 DrawGraphics objects are instantiated and as each one is made it is added to graphicsContainer and to the Vector. On line 66 the frame is shown and it will display the 8 DrawGraphics objects but the interesting behavior does not occur until the cycle method is called on line 108.
As you can see on line 78 the cycle method is an infinite loop. In this loop we will continuously ask each of the 8 DrawGraphics objects to reposition its circle and then to redraw itself. On line 83 we ask the Vector to give us a copy of its contents encapsulated in an Enumeration object. On line 85 the while statement asks the Enumeration object if it still contains any more objects and the Enumeration object either answers true or false. On line 91 the Enumeration object is asked to give us its next available object reference and we cast this object reference back into its original type (in this case DrawGraphics) and reference it with another DrawGraphics reference called dg. On line 92 we ask the DrawGraphics object that is being referenced by dg to randomly reposition its circle and on line 93 we ask it to repaint itself. When the current Enumeration object is depleted we loop back up to the Vector object, ask it for a fresh copy of the DrawGraphics object references it is holding and repeat the cycle indefinitely.
The code from line 96-100 implements a crude technique for generating a time delay but since we have not had a chance to cover Threads yet this technique will have to suffice.
This concludes lecture 5. Your next step is to do lab 5 which can be found on the main page of the class web site.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:27:29

6


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 6 - Exceptions, Sockets, Streams and Web Servers (V1.04)
PDF
Purpose
Exceptions
Streams And Sockets
Ports And Well Known Ports
webtest.SocketTest1 Class (using sockets and streams in Java)
HTML For Beginners
A Simple Web Server
Purpose
One of Java's primary strengths is that it was specifically designed for use in a networked environment and so part of learning Java includes learning how to use it for network programming. After covering exceptions (which are a very powerful part of the Java platform) this lecture will also look at an HTTP client and finally a small web server. If you have always wanted to know how these web oriented technologies worked then this lecture should be a fun one for you! Oh yes, and here is a solution to the last problem from lab 5:
Lab5Solution
Exceptions
The source code for the programs in the first part of the lecture are present in this comparenums.zip file.
In order to assure that Java programs have a uniform way to handle exceptional conditions that might occur while they are running a formal exception handling mechanism was built into the Java platform. The two primary categories of exceptions are unchecked exceptions and checked exceptions. Unchecked exceptions represent errors that cannot be handled at runtime. These type of exceptions will shut down the virtual machine and the problems that caused them must usually be fixed in the source code. Checked exceptions represent conditions in the code that can be handled during runtime and it is these type of exceptions that we are immediately concerned with.
Methods that encounter exceptional conditions that prevent them from finishing properly are declared to 'throw' specific exception objects using a throws statement. Bring up the API documentation for the Integer class in a browser and look at the detailed method description for the parseInt(String) method. Notice that this method declares that it throws a NumberFormatException object if the String it is passed can not be converted into a number. If you follow the link to the API documentation for the NumberFormatException class you will also see that it is similar to any other Java class. Somewhere in the parseInt(String) method is a line of code that throws a NumberFormatException which will look similar to the following line of code:
throw new NumberFormatException("Can not parse number.");
As soon as the line of code that is similar to this one in the parseInt method is executed the method immediately returns and control is passed off to a catch block which is designed to 'catch' NumberFormatExceptions that are thrown to it. In this course we are going to focus on the code that is used to catch exceptions instead of the code that throws them. After you are comfortable with how to catch and handle exceptions you can then study how to design methods that will throw them too.
In an earlier lecture we studied the CompareNums1 class and now we are going to revisit it. On lines 44 and 45 of CompareNums1 notice that we are using the Integer.parseInt method twice but we have not added any extra statements that will catch NumberFormatExceptions if they are thrown. Run the CompareNums1 program again, enter in improperly formatted numbers and see what happens. These methods will throw NumberFormatExceptions but since we are not catching them they are passed on to the virtual machine. The virtual machine will then print the type of exception it was passed and then it shuts down (type CTRL-C to exit back to the command line). Lets now look at a version of CompareNums1 that has some exception handling code added to it.
The CompareNums2 class is very similar to CompareNums1 except that it has a try block and a catch block added to it. Starting on line 43 is a try block which ends on line 72. This block encloses the two Integer.parseInt methods along with all the code under these methods that we do not want to run if either one of them throws an exception object. Starting on line 73 is a catch block that works with the try block and it ends on line 85. Notice that this specific catch block is designed to catch NumberFormatException objects and if either one of the Integer.parseInt methods throws one of these objects then this catch statement will catch it. If there were any other methods inside the try block that threw other types of exception objects we could have put more catch blocks under the try block in order to catch these other exceptions too.
Inside the catch block on line 76 we have decided to send a message to the NumberFormatException object telling it to print some details about itself but we did not have to do this if we did not want to. On line 79 we display a JOptionPane error message dialog which tells the user that one of the numbers they entered was not formatted correctly and after the user acknowledges this fact the program ends. The way that CompareNums2 handles NumberFormat exceptions is an improvement over CompareNums1 but it is still not very useful because the user must rerun the program in order to enter correctly formatted numbers.
The CompareNums3 class is another version of CompareNums1 that also has exception handling code added to it but unlike CompareNums2's exception handling code it allows the user to reenter the input numbers until they are correctly formatted. The block of code starting at line 32 keeps looping until the user enters in a correctly formatted number for number 1. The try block starting at line 35 allows the user to enter a number in String form using a JOptionPane and then an attempt is made to convert this String into a number. If a NumberFormatException object is thrown in this try block then the catch block on line 40 catches this exception object and handles it by informing the user about the problem and then setting the properNumber variable to false. As long as the properNumber variable is set to false the do/while loop which starts on line 32 and ends on line 54 will keep looping until the user enters a correctly formatted number. The code for entering in number 2 (which starts on line 58) is very similar to the code for entering in number 1.

Streams And Sockets
One of the main reasons for learning to program in Java is because it was specifically designed to work with the internet. Java's networking capabilities are rich and powerful and in this section we are going to explore some of the more fundamental tools that Java uses for networking including streams and sockets. Java has a wide range of higher level networking tools that are built upon the simpler streams and sockets up to and including Object serialization and RMI (Remote Method Invocation). Object serialization provides the capability to take a live object running in one JVM, 'freeze', send it through the internet to a JVM running on another machine and then 'thaw it out' so it can be used on the second machine. RMI allows objects running in different JVMs on different machines on the internet to invoke each other's methods over the internet just like methods in local objects are invoked. These higher level networking capabilities are beyond the scope of this course but the simple streams and sockets we will be working with will help you to understand the more sophisticated networking tools when you eventually get around to studying them.
A good place to start our discussion of sockets and streams is with TCP/IP (Transmission Control Protocol/Internet Protocol) and the mechanism it provides for network communications. The internet is based on the TCP/IP protocol and anything you learn about this protocol will be useful for working with almost any computer language including Java. IP is a protocol that gives each node or host on the internet a unique address and then provides the logic for routing data between these hosts. The IP protocol is designed to be overlaid on top of lower level layers like ethernet, FDDI, token ring, the Public Switched Telephone Network etc. and it makes all of these diverse lower layers look like they are part of one large network to the higher level layers that sit on top of it.
The current version of the IP protocol is IPv4 and the host addresses that it specifies consist of 4 bytes separated by periods (like 206.21.94.2 or 146.85.1.50). The next version of the IP protocol is called IPv6 and it is currently being tested on a number of experimental networks throughout the world. IPv6 has a much larger address space and is also more sophisticated than IPv4 but currently the main part of the internet still uses IPv4 and so this is what we will focus on. One of the nice things about Java is that is has classes like InetAddress that encapsulate the details of the protocol that is being used to communicate with another host on the internet and if a programmer is careful to use these classes properly then when the switch to IPv6 eventually occurs their programs will not break.
TCP is a higher level connection-oriented protocol that uses the IP protocol to provide a stable connection between two hosts on the internet. This stable connection is often called a socket with the idea being that when one host establishes a TCP connection with another host on the internet it is almost like a physical wire is being plugged into both of them through which data can be sent. Sockets provide abstractions called data streams to the applications that use them and the data that is sent through these streams by an application is guaranteed to arrive at the destination host intact and in the same order that it was sent in. UDP (User Datagram Protocol) is a connectionless protocol that also uses the IP protocol to send information between hosts on the internet but its data transmissions are not guaranteed to arrive at their destination (which means that data can be lost) and this data can also arrive in an different order than what it was sent in. In this class we will only be working with TCP sockets and streams.

Ports And Well Known Ports
The idea of a socket is very useful abstraction for thinking about how two hosts on the internet are connected together so that they can exchange information. This idea can be extended by thinking about 'where' in a host computer one might 'plug' a socket into. If a host needs to be connected to multiple other machines on the internet should they all be plugged into the same place in the host or to different places in the host? To solve this problem the concept of ports was developed and with this abstraction each host has a number of ports built into it (usually 65536 TCP ports and 65536 UDP ports) and a socket connection can be plugged into any one of them. The way that ports are used is that a piece of software called a server is written and it is attached to the back end of a given port where it listens for socket connections being plugged into the port. When a socket connection is established then an input and an output stream are opened within the socket and the server uses these streams to communicate with the client host that requested the socket connection. Ports that have servers attached to their back ends are said to offer the services that these servers provide.
At this point you may be wondering how a client host knows which services are available on what ports on any given host on the internet that it may want to communicate with. The answer to this question is that the lower 1024 ports consist of well known ports whose service-to-port mapping is maintained by IANA., the Internet Assigned Numbers Authority. Some of the more popular well known port services are listed in the following table and a more complete list can be found here:
Commonly Used Well Known Ports
Port
Service
20
FTP - File Transfer Protocol
23
Telnet
25
SMTP - Simple Mail Transfer Protocol
53
DNS - Domain Name System
79
Finger
80
HTTP - Hyper Text Transfer Protocol
As you can see the well known port for the Hyper Text Transfer Protocol (HTTP) that is used to transfer Hyper Text Markup Language (HTML) based web pages from web servers to web browsers uses port 80. If you want to see this idea in action open a web browser and type the following into its URL text field:
http://devicetop.com:80/
The :80 part of this URL specifies the port that the browser should establish a socket connection with in order to request that a resource (usually an HTML web page) be sent to it by the HTTP server that is attached to the back end of this port. If one does not explicitly specify a port number in the URL the browser will assume that it is attaching to port 80 on the destination host because it knows that this is the well known port for the HTTP service. After this page has loaded select View->Page Source in Netscape Navigator/Mozilla or View->Source in Internet Explorer in order to see the HTML code that the server sent to your browser using a data stream in the socket connection that the browser opened to it.
If you want to see what happens if you specify a port in the URL that does not have an HTTP server running on it try typing the following line into your browser's URL text field:
http://devicetop.com:81/
The browser should wait and then eventually indicate that the request timed out because there probably is not an HTTP service running on port 81 at this URL. An HTTP server can be run on any available port on a host machine but a browser can communicate with this server only if it knows what port the server is using ahead of time.

webtest.SocketTest1 Class (using sockets and streams in Java)
The source code for the programs in the last part of the lecture are present in this webtest.zip file.
Now that we have covered a bit of background material on ports, sockets and streams lets look at a small program that uses them to connect to an HTTP server on the internet. The webtest.SocketTest1 class (which is part of the webtest package) establishes a socket connection to port 80 of the host machine at www.ibutton.com, opens an input stream and an output stream to the HTTP server that is connected to port 80 and then sends an HTTP GET request to this server using the output stream. If the server has the requested resource (usually an HTML based web page) then it will send it to us using the input stream and if it does not have the resource it will send us an HTTP error message.
On line 31 a StringBuffer object is created which we will use to hold the response from the server. StringBuffer objects are more flexible than String objects because their contents can change and they can grow in size dynamically (that is why we are using one here instead of a String). On line 37 an InetAddress object is created and it will be used to hold the IP address of the host we want to connect to. We are passing a URL to the static method getByName and this method will use a DNS (Domain Name System) server to convert the domain name we passed it into an IP address. By encapsulating the IP address inside of an InetAddress object we are assuring that our code will not break when the internet moves from IPv4 to IPv6. The getByName method can throw an UnknownHostException object and the try block that this line of code is inside of will take this exception and pass it to the catch block on line 81 if this occurs.
On line 40 a Socket object is being created and the IP address of the host we want to communicate with (along with the specific port in this host we want to connect to) is passed to the Socket object's constructor. If you look at the API documentation for the Socket class you will see that the constructor we are using will throw an IOException if it can not establish a socket connection to the specified address. Not only can the code on line 40 throw an IOException but the output and input stream code on lines 43, 46, 57 and 68 can also throw IOExceptions and if any of them do the try block will send these IOException objects to the catch block on line 85.
After the socket connection is established it can be used to open input and output streams. The code on line 43 opens an output stream to the server and then this raw output stream is wrapped inside of a higher level PrintWriter object. A PrintWriter contains methods like print and println which are similar to the System.out.print and System.out.println methods that you are use to using. You may be wonder why lines 51 and 52 are not listed in the previous paragraph as throwing IO exceptions and the reason is because they don't. PrintWriter objects do not throw IO exceptions and they also send platform specific End Of Line (EOL) characters so they are not the best objects to use for network communications because hosts represent a mix of platforms and the possibility of network errors occurring is likely. The reason we are using a PrintWriter here is that it is simple and I also wanted to point out its limitations for network use. The SimpleWebServer1 class, covered later, will show a better output class to use for network communications. The last interesting thing shown on line 43 is the technique of wrapping low functionality objects inside higher functionality objects which is a pattern that is heavily used in Java because it is very flexible and modular. Notice that the input stream creation code on line 46 also uses this pattern when it wraps the raw input stream inside of an InputStreamReader object and then wraps the InputStreamReader inside of a BufferedReader.
Now that the output and input streams have been opened to the HTTP server we send an HTTP GET request to this server on line 51. The HTTP protocol is built upon readable text and to request a resource from an HTTP server one only has to send it a text based GET command along with a path to the resource you want to get. This path that specifies the location of a resource in an HTTP server is called a URI (Uniform Resource Indicator). If the path specified in the GET request is simply the root path / then the HTTP server will send a default file which is specified by the server's manager and this default file is usually the server's default web page in HTML format. If you comment out line 51 and uncomment line 50 then the program will request the /TINI/index.html resource instead of the / default resource. The flush method on line 52 makes sure that all the characters we have placed into the stream's output buffer have been sent to the remote server.
The while loop on line 57 reads each line that the HTTP server returns to us from the input stream as a String until a null String is encountered (which indicated that the transmission is complete). As each line is received it is printed to standard out on line 60 (which is very inefficient but useful to see for testing purposes) and it is also appended to the StringBuffer on line 63. On line 64 a newline character is added to the end of every line that is placed into the StringBuffer so that if the StringBuffer is printed the lines are easier to read.
The last interesting thing that this class does is to instantiate a JTextArea object on line 73 and initialize it with a String version of the contents of the StringBuffer. This JTextArea is then configured on lines 74-76, placed into a JScrollPane object on line 77 and then the JScrollPane and its contents are displayed in a JOptionPane dialog box on line 78. When you look at the contents of the file that the HTTP server sent us you will notice that it is the same HTML code that we saw earlier when we had the browser show us the page source for www.ibutton.com's main web page. In this section we discussed a client that used a socket and streams to request a resource from an HTTP server. In the next section we will introduce some fundamental HTML concepts for people who have not been exposed to them yet and in the final section we will program our own small web server using Java.

HTML For Beginners
If you are already comfortable with how HTML works feel free to skip this section and if you have not been exposed to it yet don't worry, this section will get you started. HTML consists of markup tags that enclose sections of a document (usually text) which tell a browser how to draw these sections when the browser tries to display them. Lets explore this idea a bit more by thinking about how books were made in the 1950s. The author would typically type the text for a book on a typewriter and then send this typed version to a publisher. The author's typed version of the book would not be in an appropriate form for the final version of the book and so the publisher would somehow have to change the typed form into a final form that was suitable for use in a book.
In order to communicate to the people who were responsible for setting up the type for the printing press that was used to print the final version of the book, a layout editor would write shorthand notes (markup tags) on the author's typed pages near various sections of text that would tell the typesetters how these sections of the book should look in the final version of the book. These shorthand notes would indicate how big titles should be, where bold text was, where underlined text was, etc. and these notes were (for the most part) standardized so that many layout editors could easily communicate with a large number of typesetters across the whole printing industry.
Here is a link to a small HTML file called simpleHTMLpage on the classes' web site. Open this file in a separate browser window to see what it looks like and then view its page source (like we did earlier) to see what the HTML markup tags look like that generated it. All HTML files must contain an opening HTML tag and a closing HTML tag and the complete contents of the HTML file must be placed between these tags. You can see that a closing HTML tag is simply the opening tag with a / before it. Inside these main HTML tags an HTML document is divided into a header and a body by and tags. Inside the head section of simpleHTMLpage is a title that is set within a tag. When the page is rendered by a browser the title tags tell the browser to place this title up in its title bar.
Inside the body of an HTML document is where most of the interesting information is placed. In SimpleHTMLpage's body is some text enclosed within

tags and these tags tell the browser to display this text in a large bold font. The tags tell the browser to display text in bold and the tags tell it to underline text. The
break tag tells the browser to drop down to the beginning of the next line and it does not have a closing tag. You will find that HTML has a number of improperly formed tags like this in it and that is why XHTML needed to be developed in order to fix this problem (XML and XHTML are very fascinating topics that you will eventually need to know about but unfortunately we do not have enough time to explore them further here). The last thing I want you to do is to retype the HTML code that is shown in the browser's page source window into jEdit (or your favorite editor), save it under another name and then open this new file in a new browser window. The browser should display the same page as simpleHTMLpage does.

A Simple Web Server
The class webtest.SimpleWebServer1 is a simple HTTP web server that listens on port 8080 for socket connections. When a socket connection is made and an HTTP GET request comes into the port, the server sends back a default HTML page that will then be displayed in the browser. The web server runs continuously until CRTL-C is pressed in the server's shell window and if you are running this server on a machine that is connected to the internet and which has a routable IP address then anyone on the internet who has this address can connect to it and receive the web page it serves. Lets test this server now and then we will look at its code. Compile and then run the webtest.SimpleWebServer1 class on your machine and notice what IP address it says your machine has. Lets assume that the IP address it prints is 206.21.94.66 (your address will be different). Bring up a browser on the same machine you are running the server on and then type the following into the browser's URL text field:
http://206.21.94.66:8080/
Please do not forget to substitute your machine's IP address for 206.21.94.66!
You should get a web page served to your browser that has the text This is your Java server's default web page. displayed on it along with some text which indicates how many times the page has been served. If you have access to another machine connect to your server from it or if you have any friends anywhere in the world who are currently on the internet contact them and have them try to access your server. Notice that since the web server is listening for socket connections on port 8080 that we have to explicitly specify this port in the browser's URL text field. If you changed the port from 8080 to 80 in the classes' source code and ran it on a machine that did not already have an HTTP server listening to port 80 then you would not need to specify the port to connect to in the browser's URL text field.
Lets look at the source code for webtest.SimpleWebServer1. I am not going to cover what the try/catch blocks are doing because we covered most of this information earlier in the webtest.SocketTest1 class and we do not need to repeat it here. The block of code starting on line 36 simply discovers the IP address that the server is running on and it saves this information in an InetAddress object and in a String. On line 57 a ServerSocket object is instantiated and we are passing it the port we want it to listen on along with the number of socket connections it will queue before it starts to refuse socket connections. On line 61 a short message is printed to standard out which tells the server's administrator what the IP address is of the machine the server is running on.
The while loop that starts on line 66 is the main loop in the program and it is designed to loop continuously until the server's administrator types CTRL-C in the shell window that the server is running in. On line 70 the ServerSocket's accept method is invoked and this method will wait (block) until it receives a socket connection on port 8080. When a socket connection is made this connection is encapsulated in a Socket object which is then returned and referenced by the clientSocket variable. This Socket object works just like the Socket object we studied earlier in the webtest.SocketTest1 class and so you should be familiar with how it operates. On line 73 the Socket is passed to the handleClientRequest helper method which will then use it to open an input stream back to the client so that the client can send us its request.
Lets move down to the handleClientRequest helper method which is on line 93 and look at it. Notice that this method is marked private which means that it is only accessible within this class. Since it is a helper method and not part of the classes's API it does not have to be visible outside of the class. Also notice that this method has elected to re-throw any IOExceptions it encounters back to the code that called it because the calling code is in a better position to deal with these exceptions than it is. On line 103 the Socket object is used to open an input stream back to the client and the while loop starting on line 106 reads the client's request one line at a time and prints this information to the server's standard out. Line 108 inside of this while loop has an if statement that is used to grab the first line sent from the client (which contains the HTTP command the client is sending) and save this String using the httpCommand String reference for later use.
The if statement starting on line 123 checks to see if the client has sent an HTTP GET request and if it has then it will service this request by sending the default HTML web page back to it. For now if any other command was sent by the client the socket connection is closed without sending a response and the server starts listening for another socket connection. Inside this if statement on line 131 the prepareHTMLResponse helper method is invoked and it will assemble the default HTML web page for us and return it as a StringBuffer. On lines 135 and 136 we use the Socket to open an output stream back to the client and then send the default web page back to the client using this stream.
The prepareHTMLResponse helper method which starts on line 167 simply assembles the HTTP header and HTML code (that serves as the default web page) into a StringBuffer and returns it to the caller. The block of code starting on line 171 clears out the two StringBuffers that are used to assemble the HTML web page and the HTTP header. We are using StringBuffers instead of Strings here because they are quicker and they use less resources than String objects do. The block of code starting on line 175 assembles the HTML web page and this HTML code is similar to the code in the simpleHTMLpage that we covered earlier with one major exception. On line 181 a bit of magic occurs in that a piece of live code (the hitCount variable) is used to generate dynamic HTML content that changes everytime the default web page is served and this small technique just hints at what is possible if dynamic HTML content needs to be served to a browser.
The block of code starting on line 186 assembles the HTTP header for the default web page and the code on line 192 concatenates the header and HTML web page together into one StringBuffer object. On line 195 this StringBuffer is returned to the calling code and the method ends.
The last thing we need to cover in this program is the finally block which is present on line 151. Finally blocks are used to hold code that must be executed after the code within a try block is through running regardless of whether an exception was thrown or not. Finally blocks are a good place to put cleanup code like closing streams and socket connections and this is exactly what we are using it for here.
This concludes lecture 6. Your next step is to do lab 6 which can be found on the class web site.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:24:29

7


JavaDevices
> javacourses > foundation_module > lectures

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lecture 7 - Arrays, Threads and Polymorphism (V1.02)
PDF
Purpose
Java Arrays
Java Threads
Polymorphism
Purpose
This is the last lecture which is devoted to general Java topics and in it we will be discussing arrays, threads and polymorphism. The general Java lectures in this course have been designed to give Java beginners a quick tour of some of the more essential and interesting aspects of the Java platform and language. Keep in mind that if the Java platform and language were considered to be an iceberg these lectures have given a quick tour of the small fraction that floats above the surface of the water.
If you like what you have seen of Java so far then I would encourage you to continue to seriously study it by reading Java books and articles, visiting Java and Object oriented websites and looking through Java source code. As was stated in lecture 1 Java is a highly engineered technology that takes a considerable amount of effort to master but any time you spend learning it is an investment that will pay handsome dividends.

Java Arrays
Arrays are a necessary part of any programming language and Java is no exception to this. We were, however, able to delay discussing them until now by using Vectors for things we would have normally used Arrays for earlier in the class. In Java Arrays are objects that hold a fixed number of data elements that are all of the same type. For example we can have an array of ints, Strings, doubles, floats, StringBuffers, JButtons, and even Objects. Arrays can tell you how many members they hold when asked and they can be passed into methods and returned by methods just like primitive data types and regular objects.
Open the ArrayTest program in another browser window and lets walk through it. Before we look at the arrays themselves take a look at the package command that is on line 7 (you can also download the arraytest.zip file which contains the Java source code for this program). This package command is longer than the ones we have been using and it is more typical of the packages that you will encounter when you work with Java software that is meant to be used for more than just testing and educational purposes. As a reminder, in order to compile and run this program the files will need to be placed in a folder hierarchy called org\javadevices\javaclass.
Inside the main method on line 66 an array reference of type String called tools is being declared and one can tell it is an array reference by the braces that follow the String type declaration. In Java it is also acceptable to place the array braces after the reference name instead of the type name but most Java programmers seem to prefer placing the braces after the type name. On the right side of the equals sign a new String array object is being instantiated and it is also being initialized with the Strings which are contained within the curly braces. This String array object will contain 5 Strings and after it is done being instantiated it will be attached to the reference .
On line 72 an array reference of type int called toolWeights is being declared and other than the fact that it is an integer array the instantiation of the array object to the right of the equals sign is similar to the String array described in the previous paragraph. The numbers in this array are the weights of the tools which are in the String array with each weight being in the same position as the tool it corresponds with in the String array.
On line 74 the printTools method is called and both the tools and toolWeights references are passed to it. Inside the printTools method on line 25 the getLetterCount method is called and only the String array is passed to it. The getLetterCount method is designed to analyze the String array that is passed into it and determine how many letters are in each String in the array. It creates a new empty integer array on line 44 called letterCount and we are asking the passed -in String array how many members it contains in order to tell the integer array how many members long it needs to be. Notice that when we ask the array its length we are not invoking a method in the array but instead we are directly accessing a public instance variable that holds the length.
On line 46 an integer variable is created which will be used to index both the String array and the integer array that will hold the letter counts. The while loop which starts on line 47 will loop until all the members in the String array have been processed. On line 49 each String in the String array is selected in turn and its length method is invoked to determine how long the String is (and yes it is interesting how the length of arrays is determined by accessing a public instance variable and the length of Strings is accessed by invoking a length method!). This length is then copied into the letterCount array in the position that is analogous to the word it is matched with in the String array. After all the Strings in the String array have been processed the integer array which contains the letter counts for these Strings is returned to the caller on line 53.
Back on line 25 the returned integer array is referenced by toolsLetterCount and finally the names of each of the tools in the String array along with their weights and letter counts are printed to standard out in the for loop on line 29.

Java Threads
Another one of the many interesting things about Java is that it is multithreaded which means that it is able to have multiple objects running concurrently with each other. Threads are similar to the processes or tasks used in multiprocessing or multitasking systems except they are 'lighter weight' and they take less resources to implement than a process or a task. Concurrency means that in a single processor system really only one thread can be running at any instant in time but from the point of view of the outside world these threads appear to be running at the same time. For most purposes one can think of the Java objects that one sets up to run on their own threads as running in parallel with each other almost as if each of these object was running on its own private little computer system. In this class we will only touch the surface of threads but the topic is very rich and deep and hopefully you will become intrigued enough with threads to study them further on your own.
In Java the two ways to create an object that can run on its own thread are to either have it extend the Thread class or have it implement the Runnable interface. Of these two, object oriented architects usually prefer to have a class implement the Runnable interface because most classes do not have a conceptual 'is a' relationship with Thread and usually a class should only extend a parent class if it is conceptually a specialization of this parent. As an example a web server object that will be running on its own thread is conceptually a web server not a Thread and so it would be better to have it implement the Runnable interface instead of extending Thread. Having said that, you will find that extending Thread is a very widely used technique in Java and if you choose to sometimes do this too the object police will not hunt you down and and arrest you!
Both the extending Thread technique and the implementing Runnable technique involve putting the primary behavior that the thread is going to implement inside a run method. A class that extends Thread inherits and overrides this run method and a class that implements the Runnable interface needs to implement the run method. After an object is created (using either technique) that runs on its own thread this thread can be started, put to sleep, interrupted, have its priority changed, etc. We are now going to explore two multithreaded classes to show you what multithreaded programming looks like. The first class extends the Thread class and the second class is a version of the first class that implements the Runnable interface.
Download the threaddemo.zip file, unzip it, compile the ThreadDemo1 class and run it. You will notice that this class prints the numbers 1 through 10 on the screen at different rates. This class instantiates 10 different objects and places each one on its own thread. These objects are given a unique number between 1-10 when they are instantiated and they are programmed to print this number to the screen at different pre-defined rates. On line 10 notice that this class extends Thread and so it inherits all of Thread's attributes and behaviors. The instance variables on lines 13 and 16 keep track of each instance's unique number along with how many spaces should be placed in front of this number when it is printed. The constructor, which starts on line 20, receives an integer and it uses this number for the thread's unique number and to calculate how many spaces this thread should put in front of this unique number when it is printed. The for loop on line 72 instantiates 10 ThreadDemo1 objects and then starts each of their threads running on line 77.
The last thing we need to look at in this class is the run method which starts on line 44. This method was inherited from the Thread class and it is designed to be overridden so that a thread's behavior can be implemented in it. The behavior for this class is to sleep for a set number of milliseconds (thousandths of a second) then to wake up and print the instance's unique number to standard out continuously until the JVM is shut down (by typing Control-C in the shell window). Two popular patterns that many run methods use is to implement a loop that either runs continuously with no sleeping or sleeps most of the time and wakes up periodically (our run method used this second pattern). When this class is executed the pattern it produces on the screen is interesting and it is amazing to think that it is being generated by 10 different objects running on separate threads (for the most part) independently from one another.
ThreadDemo2 is almost identical to ThreadDemo1 except that it implements the Runnable interface instead of extending Thread (as can be seen on line 10). The only other difference is how objects that implement the Runnable interface are run on their own thread. On line 75 a ThreadDemo2 object is instantiated but then on line 79 a Thread object is also instantiated and an object that implements the Runnable interface is passed to it. Since ThreadDemo2 implements the Runnable interface its objects can be passed to a Thread object's constructor with no problem. Finally on line 83 each Thread object is told to execute the run method of the object that was passed to its constructor by calling the Thread's start method.

Polymorphism
In an earlier lecture we talked about inheritance and now we need to look at an aspect of inheritance called parametric polymorphism. With inheritance a class is able to extend a parent classes' attributes and behaviors and then add to these its own attributes and behaviors. Since a child class can do at least as much as its parent can do then objects of the child class can be used anywhere objects of the parent's class is expected. This idea is not only limited to a classes' immediate parent but to any of its ancestors up to and including the Object class. Polymorphism is based on the idea that it is often useful to purposefully refer to objects of a given class using a reference typed as one of that classes' ancestors instead of the type of the class itself. What is polymorphism then? Polymorphism is the ability to reference an object of a given class using a reference typed as one of the classes' ancestors but (and here is the important part) when a method is invoked on this object the overridden behavior of the child is what is used and not the behavior of the ancestor. Perhaps this should have been called polybehaviorism (many behaviors) instead of polymorphism (many forms).
You might not grasp this concept and why it is useful by just reading a definition so lets explore it in some more depth. Download the polymorphismdemo.zip file, unzip it, and then compile and run the PolymorphismDemo1 class that you find there. In order to understand what this class is doing you will first need to look at the runtime API documentation for the Object class. In Object's API documentation page you will see that one of the methods that the Object class defines and which all Java classes inherit is the toString method. The purpose of this method is to allow an object to return a string description of itself. You may not have noticed it but methods like System.out.println use the fact that all Java objects have a toString method to 'print' objects that are passed to them as parameters. The Object classes' default behavior for this method is to print the name of the class that the object belongs to along with its hash code but since this behavior is not too useful this method is usually overridden by child classes.
PolymorphismDemo1 demonstrates polymorphism by using some classes that represent the various ranks in the US military (from Private to Sergeant Major). We start with a Person class that explicitly extends the Object class on line 75. Any class that does not explicitly extend a class automatically extends the Object class but I wanted to emphasize that Person extended Object so I showed this explicitly. As you can see Person overrides the toString method that it inherits from Object and then replaces its behavior with behavior that states 'I am just a Person, I have no rank'. On line 89, ArmyPrivate then extends Person and overrides the toString method again with behavior that states ArmyPrivate's rank. Each subsequent class extends the previous class, overrides the toString method it receives from this class and replaces it with its own behavior.
Now that you see what the relationships between these classes are we need to discuss what it means. When a Person enters the US Army they are given the rank of Private. A Private can do anything a Person can do plus specific things that their military training teaches them including how to shoot a rifle, navigate over land, dig a foxhole, etc. The next level in rank above a Private is a Private First Class (PFC) and a PFC can do everything a Private can do plus extra things that PFC's are trained to do. This inheriting and extending pattern is used all the way up to a Sergeant Major. Now lets look at polymorphism in action. On line 13 a Vector is created and what we are going to do is to create an instance of each rank class (plus an instance of Object) and place a reference to each of these instances into the Vector on lines 17-26.
In order to understand how and why Java uses polymorphism you must first grasp why it is sometimes useful to treat things in the physical world generically instead of specifically. The ironic thing is that you already have a solid understanding of what polymorphism is and what it does because it is widely used in the physical world, you just are not aware of it. Can you think of any situations where the Army might want to treat its personnel generically instead of specifically? Lets take the following scenario. The Army needs to transport a large number of its personnel overseas in a ship and we can imagine them standing on a pier ready to board. Does the ship provide a unique way for people in each Army rank to board the ship? No, of course not. The ship is meant to hold people and so the boarding gang planks are designed to accommodate the way people would board a ship (walking) regardless of what their ranks are.
In fact everything on the ship is designed to work with people not Army ranks including the showers, bathroom facilities, mess halls, and sleeping bunks. Of course the Army personnel would be segregated into different parts of the ship according to rank but these parts of the ship are not designed with military rank in mind. For the most part the crew of the ship does not really care what the ranks are of the Army personnel 'cargo' they are transporting and so they will tend to also just treat them as people. It should also start to become clear to you what the advantages are of treating the Army personnel generically as people instead of specifically by rank. For instance if the ship treated each Army person by their rank then there would have to be special eating utensils for Privates, PFCs, Corporals etc. Each rank would get a blanket and pillow specifically designed for that rank and each rank would drink a special kind of liquid. Obviously this would be no way to run a ship.
When the ship reaches its destination the Army personnel are offloaded and then they can resume the behaviors that their ranks imply. Of course there are still situations where it is advantageous to treat Army personnel generically instead of specifically by rank. The eating utensils in the mess halls still do not care what the rank of the person that is using them is, military vehicles are still designed for any person to use and latrines still accommodate any person generically regardless of rank.
So far this example has explained why it is sometimes advantageous to treat things generically instead of specifically but it still has not illustrated polymorphism. To see polymorphism in action imagine that one of the ship's crew has been ordered to do a survey of what the Army personnel think of their accommodations aboard the ship (I have been informed by some of my friends that have been in the military that this scenario is not as funny as I intended it to be!). This crew member (being ignorant of the Army's arm-patch to rank mapping) is going to randomly wander around the ship and survey any Army personnel he encounters. In the context of the PolymorphismDemo1 program the crew member can be thought of as using a generic Person reference in order to access the Army personnel instances on the ship. Now comes the polymorphism part. At the end of the survey the crew member needs to record the rank of the Person that he just interviewed and so he asks them what their rank is and even though he is referencing them generically as a Person they momentarily morph into what they specifically are to tell him their Army rank.
Moving back to the code, the demonstration of polymorphism occurs in the tellRank method which begins on line 32. On line 34 the Vector is asked to return a copy of all the object references it contains as an Enumeration (Vectors and Enumerations do not hold the objects themselves just references to them). On line 36 a generic variable of type Object is created and we are going to use this variable to hold each reference that the Enumeration gives us so that we can talk to the object that the reference refers to. Even though the above Army example used a Person as the generic reference we are going to go one class above that and use an Object reference because it is a common thing to do in Java and also because Vectors and Enumerations use generic object references internally to hold any object passed to them. They are like the ship described above that only wants to treat objects given to them generically, not specifically.
The while loop on line 40 keeps cycling until all of the object references in the Enumeration have been removed. Are you ready now to see polymorphism in action? Do not blink because you might miss it! On line 47 the Enumeration is asked to give us the next object reference in its collection and instead of casting it back into what it specifically is we reference it using a generic Object reference. Finally on line 53 Java sees that we want to concatenate the object with a String before it is passed to the println method and so the object's toString method is invoked (to obtain the object's string representation) but instead of getting the Object classes' behavior for this method we get the behavior for the object's actual type. Here is the output from this program:
Rank list:
java.lang.Object@2f6684 I am just a Person, I have no rank Rank: ArmyPrivate Rank: ArmyPrivateFirstClass Rank: ArmyCorporal Rank: ArmySergeant Rank: ArmyStaffSergeant Rank: ArmySergeantFirstClass Rank: ArmyMasterSergeant Rank: ArmySergeantMajor
Notice that even though each of the objects was being referenced using a generic Object reference the unique behavior they had implemented for the toString method they inherited and overrode was polymorphically invoked instead of the Object classes' behavior for this method.
This is the end of lecture 7. Lab 7 can be found on the class website.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:24:04

8


JavaDevices
> javacourses > foundation_module > labs

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lab 1 - Tools Download Lab (V1.2.9)
PDF
Purpose
1. SDK1.4
2. WinZip or equivalent
3. SDK1.4 documentation
4. JEdit or equivalent
Purpose
The purpose of this lab is to download the following tools in the order that they are listed and install them. I am assuming that you are using Windows 95/98/NT/2000 for this class but since Java is platform independent other operating systems that support the Java SDK1.4 (like Linux) will work too (but you may need to modify the instructions a bit to suit your operating system). Keep in mind that all of the following tools are free except for WinZip which is shareware. For those of you that are use to paying for your software development tools this might be a bit of a change.
One last thing I want you to keep in mind is that Java does have a number of GUI IDEs available for it that allow developers to create Java programs in a manner similar to the way that VisualBasic or VisualC++ does but when you are learning Java it is best to learn it with the plain and boring command line tools. There are many skills that you will learn with the command line tools that your would never encounter with the GUI IDEs and in order to use the GUI IDE's to their full potential these skills must be mastered.

1. SDK1.4
Download J2SE 1.4.2 ( http://java.sun.com/j2se/1.4 ) Offline Installation
There are two types of PC oriented Java downloads available, one for developers who want to develop Java programs and one for users who only want to run Java programs. The JRE (Java Runtime Environment) contains just enough resources to run Java programs and it is meant for users. The SDK (Software Development Kit) is meant for developers who want to develop Java programs and it comes with a JRE along with a compiler and other tools that Java developers will find useful. I recommend that you have at least a 400Mhz CPU and at least 128MB of RAM in order to run the SDK.
The SDK for Windows is about a 50meg download. After it is downloaded double click on the downloaded file and have it install the SDK into your C: root directory or into the root directory of any drive you have enough space on (the installer will create a folder called jdk1.4XXX and place all of the needed files into this directory, rename this folder to be just jdk1.4). Make sure that the demo files are selected for installation along with the rest of the SDK files. During the installation process not only will SDK1.4 be installed on your machine so that you can develop and run Java programs locally but the JRE1.4 plugin will also be installed into any browsers you may have on your machine so that Java 2 (the 2 means platform 2) and above Applets can also be run inside these browsers.
The SDK comes with some demo programs that do a good job of showing off Java's capabilities. Here is how to run two of the more interesting demos:
Open up an MSDOS window (START -> Programs -> MS-DOS Prompt) and type the following at the command prompt to run the first demo (I am assuming that you have installed the SDK in C: drive but if not just use the letter of the drive that you did install it on instead of C). MAKE SURE YOU TYPE SwingSet2.jar and Java2Demo.jar WITH THE UPPER AND LOWER CASE LETTERS EXACTLY AS SHOWN (Java is very case sensitive).
cd c:\jdk1.4\demo\jfc\SwingSet2 enter
c:\jdk1.4\bin\java -cp .\ -jar SwingSet2.jar enter
The second demo can be run by typing the following at the MSDOS command prompt:
cd c:\jdk1.4\demo\jfc\Java2D enter
c:\jdk1.4\bin\java -cp .\ -jar Java2Demo.jar enter
The bin directory inside the jdk1.4 directory contains all of the command line tools that come with the SDK along with the JVM launcher. The java.exe file in this bin directory runs the JVM.

2. WinZip or equivalent
The SDK's documentation comes in .ZIP format and you will need a .ZIP utility to extract it. Beyond this Java likes to deploy its programs and libraries in .JAR (Java Archive) files to reduce network transfer time and also to keep a program's resources organized and manageable. .JAR files are very good at doing this. The interesting thing is that .JAR files are nothing more than .ZIP files with a .jar extension and so .ZIP utilities can be used to work with .JAR files too. The reason that I have specified WinZip ( http://winzip.com/ ) or equivalent is that we are going to spend some time poking around inside the Java library files that come with the SDK and other Java programs and WinZip's .ZIP file scanning ability is very handy for doing this.
When installing WinZip choose Start with WinZip Classic instead of Start with WinZip Wizard at the appropriate screen.

3. SDK1.4 documentation
As stated in step 2 above the SDK1.4 documentation ( http://java.sun.com/docs ) comes in .ZIP format. Download the documentation bundle and extract it into your jdk1.4 directory . When the documentation is extracted your jdk1.4 directory should have a docs directory in it.
If you are uncomfortable using WinZip you can use the jar.exe command line utility that comes with the Java SDK (jar.exe is in the jdk1.4\bin directory). In order to use the jar utility to unzip the documentation, copy the documentation's .zip file into the jdk1.4 directory. Open up an MSDOS window (START -> Programs -> MS-DOS Prompt), change to the jdk1.4 directory that contains the documentation's .zip file and type the following command:
c:\jdk1.4\bin\jar -xvf filename.zip enter
This should create a docs directory inside of the jdk1.4 directory and extract the SDK documentation into it.
When you are done installing the documentation your c:\jdk1.4 directory should contain the following sub-directories:
bin demo docs include jre lib

4. JEdit or equivalent
Java source code is saved in raw text format and it has a .java extension. In order to work with and save text files one needs to use a text editor and JEdit is a 100% pure Java text editor that was specifically designed for programmers. Your are free to use any text editor to develop your Java programs but JEdit is especially powerful and user friendly and if you want to see what a commercial quality cross platform GUI Java program looks and feels like this is your chance.
Download JEdit 4.2 (http://jedit.org/ the download link is in the upper right corner of the page ), read the installation instructions and install it on your computer. Keep in mind that the SDK from step 1 above must be installed on your computer before you can install and run JEdit. The only thing that I would add to the installation instructions is to provide the full path to the java executable when running the installer:
Instead of typing java -jar jedit42install.jar to install jedit
type c:\jdk1.4\bin\java -jar jedit42install.jar assuming that you installed the SDK into your C: drive's root directory.
Take the defaults that the installer gives you. After the install process JEdit should be installed into the C:\Program Files\jEdit 4.2 directory. When you run JEdit for the first time it might ask you where the java runtime is. Point it to the jre/bin/java.exe file that is inside of the jdk1.4 directory and it should run fine from there.
After you get JEdit running you might want to create a shortcut to the JEdit launch icon (which is in the jEdit directory inside of the Program Files directory ) and place this shortcut on your desktop.
Finally, JEdit has a number of very useful plugins (accessed through the Plugins menu) that enhance the functionality of the editor. I highly recommend at least installing the Buffer Tabs plugin.
This is the end of lab 1. If you have any questions or are experiencing problems feel free to use the class email list.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:23:27

lab 9


JavaDevices
> javacourses > foundation_module > labs

the JavaDevices site
Home

Home
Index
Email List
JavaDevices Site
Foundation_module
Lectures
Lecture 1
Lecture 2
Lecture 3
Lecture 4
Lecture 5
Lecture 6
Lecture 7
Labs
Lab 1
Lab 2
Lab 3
Lab 4
Lab 5
Lab 6
Lab 7
1-Wire_module
Lectures
Lecture 1
TINI_module
Lectures
Lecture 1


Lab 2 - Adding Methods Lab (V1.1.1)
PDF
Purpose
Question 1
Purpose
The purpose of this lab is to add some methods to the Hello.java program that was presented in lecture 2

Question 1
Add the following methods to the Hello.java program that was given in lecture 2 and test them:
public void printNums(), prints the numbers from 1 to 50 using a loop.
public void setMessage(String mess), copies the String that is passed as a parameter to this method into the object's message instance variable (look at the constructor for hints on how to do this).
public void printPattern(), prints the following pattern when invoked:***************Hint, System.out.print() prints to the screen without issuing a newline while System.out.println() issues a newline when it is done printing.
This is the end of Lab 2. Good luck and if you have questions post them in the forum.

Copyright © 2005 JavaDevices. All rights reserved.
- Last Published: 10/13/2005 09:22:56

lap 10

0 Comments:

Post a Comment

<< Home

MySpace Layouts
MySpace Layouts