Experiment 2

Polymorphism, Exception and GUI

1, Objectives

1)Inheritance and Polymorphism

2)Exception handling

3)GUI application

4)Graphics

2, Contents

1)The following is a program in C#. Try to translate it to Java program. [Hints: use Java interface with an only method to replace the C# delegate type; use the instance of Java inner class (implements an interface ) to replace the C# delegate instance; List> in C# is corresponding to ArrayList> in Java. ]

class Delegates{

// delegate for a function that receives an int and returns a bool

public delegate bool NumberPredicate( int number );

static void Main( string[] args )

{

int[] numbers = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

// create an instance of the NumberPredicate delegate type

NumberPredicate evenPredicate = IsEven;

// call IsEven using a delegate variable

Console.WriteLine( "Call IsEven using a delegate variable: {0}",

evenPredicate( 4 ) );

// filter the even numbers using method IsEven

List< int > evenNumbers = FilterArray( numbers, evenPredicate );

// display the result

DisplayList( "Use IsEven to filter even numbers: ", evenNumbers );

// filter numbers greater than 5 using method IsOver5

List< int > numbersOver5 = FilterArray( numbers, IsOver5 );

// display the result

DisplayList( "Use IsOver5 to filter numbers over 5: ",

numbersOver5 );

} // end Main

// select an array's elements that satisfy the predicate

private static List< int > FilterArray( int[] intArray,

NumberPredicate predicate )

{

// hold the selected elements

List< int > result = new List< int >();

// iterate over each element in the array

foreach ( int item in intArray )

{

// if the element satisfies the predicate

if ( predicate( item ) )

result.Add( item ); // add the element to the result

} // end foreach

return result; // return the result

} // end method FilterArray

// determine whether an int is even

private static bool IsEven( int number )

{

return ( number % 2 == 0 );

} // end method IsEven

// determine whether an int is positive

private static bool IsOver5( int number )

{

return ( number > 5 );

} // end method IsOver5

// display the elements of a List

private static void DisplayList( string description, List< int > list )

{

Console.Write( description ); // display the output's description

// iterate over each element in the List

foreach ( int item in list )

Console.Write( "{0} ", item ); // print item followed by a space

Console.WriteLine(); // add a new line

} // end method DisplayList

} // end class Delegates

publicclass Delegates {

interface NumberPredicate{

void number(int number);

returnboolean value1;

};

privatevoid IsEven()

{

int number;

if(number%2==0)

System.out.println("No!");

else

System.out.println("Yes!");

}

private void IsOver5( int number )

{

if(number<=5)

System.out.println("No!");

else

System.out.println("Yes!");

return ;

} // end method IsOver5

// display the elements of a List

publicstaticvoid main( String[] args )

{

NumberPredicate a=newNumberPredicate(){

publicvoid value(){

System.out.println(" ");

}

};

ArrayList list = newArrayList();

int[] numbers = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

Delegates evenPredicate = new Delegates();

System.out.println( "Call IsEven using a variable: " );

evenPredicate.IsEven();

evenPredicate.IsOver5(9);

// filter the even numbers using method IsEven

list.evenNumbers = FilterArray( numbers, evenPredicate );

// display the result

DisplayList( "Use IsEven to filter even numbers: ");

// filter numbers greater than 5 using method IsOver5

list.numbersOver5 = FilterArray( numbers, IsOver5 );

// display the result

DisplayList( "Use IsOver5 to filter numbers over 5: ");

} // end Main

// select an array's elements that satisfy the predicate

privatestaticlist FilterArray( int[] intArray,NumberPredicate predicate )

{

for ( int item : intArray )

{

// if the element satisfies the predicate

if ( predicate( item ) )

list.Add( item ); // add the element to the result

} // end for

returnlist;

}// end method FilterArray

// determine whether an int is even

privatestaticvoid DisplayList( String description, ArrayList< int > list )

{

System.out.println( description ); // display the output's description

// iterate over each element in the List

for ( int item : list )

System.out.println( "{0} ", item ); // print item followed by a space

System.out.println(); // add a new line

} // end method DisplayList

}// end class Delegates

2)A simple calculator

A.To develop a simple calculator that can read a string with calculating expression (addition, subtraction, multiplication, division of two integers ) and print the result.

B.Because the calculating expression of addition, subtraction, multiplication, division is very similar (e.g. 3+2, an integer + an operator + an integer), we can declare an interface ICalculator, with an only method int calculate(String expression). For each operation, a class can be created to implement the interface ICalculator.

When calculating, the input string expressionmust be analyzed to extract the operands (e.g. 3 and 2) and the operator (e.ge. +). The analysis is common to four calculation classes. So it’s reasonable to create an abstract class AbstractCalculator, which contains a method int[] split(String expression, String deliString). And the four implementing class can inherit AbstractCalculator.

C.Steps:

(1)create an interface ICalculator, with a method int calculate(String expression).

(2)create an abstract AbstractCalculator, with a method int[] split(String expression, String deliString). deliString is the separator betwe

en two operands。

Hints: Call split() method of class String to split the expression. Call parseInt() method of class Integer to convert a string to a integer.

(3)create the following classes to implementICalculator, and inherit from AbstractCalculator:

Plus

Minus

Multiply

Divide

Default,when the input expression can’t be analyzed and calculated。

(4)create a classTest: read user input, call the proper instance, and print the result.

ICalculator calculator;

if (expression.indexOf("+") != -1) {

calculator = new Plus();

} else if (expression.indexOf("-") != -1) {

calculator = new Minus();

} else if (expression.indexOf("*") != -1) {

calculator = new Multiply();

} else if (expression.indexOf("/") != -1) {

calculator = new Devide();

} else {

calculator = new Default();

break;

}

The class hierarchyis as followings:

package AbstractCalculator;

import java.util.Scanner;

interface ICalculator

{

publicint calculates(Stringa);

}

publicclass AbstractCalculator

{

publicstaticvoid main(String[] args)

{

ICalculator calculator;

Stringexpression;

Scanner n=new Scanner(System.in);

expression=n.nextLine();

if (expression.indexOf("+") != -1)

{

calculator = new Plus();

}

elseif (expression.indexOf("-") != -1)

{

calculator = new Minus();

}

elseif (expression.indexOf("*") != -1)

{

calculator = new Multiply();

}

elseif (expression.indexOf("/") != -1)

{

calculator = new Divide();

}

else

{

calculator = new Default();

}

System.out.println("Result:"+calculator.calculates(expression));

}

}

abstractclass AbstractCalculators

{

publicint[] split(Stringb,StringdeliString)

{

int[] n=newint[10];

n[0]=b.indexOf(deliString);

n[1]=b.indexOf(deliString)+1;

int[] m=newint[10];

m[0]=Integer.parseInt(b.substring(0,n[0]));

m[1]=Integer.parseInt(b.substring(n[1]));

returnm;

}

}

class Plus extends AbstractCalculators implements ICalculator

{

publicint calculates(Stringa)

{

int[] l=split(a,"+");

returnl[0]+l[1];

}

}

class Minus extends AbstractCalculators implements ICalculator

{

publicint calculates(Stringa)

{

int[] l=split(a,"-");

returnl[0]-l[1];

}

}

class Multiply extends AbstractCalculators implements ICalculator

{

publicint calculates(Stringa)

{

int[] l=split(a,"*");

returnl[0]*l[1];

}

}

class Divide extends AbstractCalculators implements ICalculator

{

publicint calculates(Stringa)

{

int[] l=split(a,"/");

returnl[0]/l[1];

}

}

class Default extends AbstractCalculatorsimplements ICalculator

{

publicint calculates(Stringa)

{

System.out.println("Input Error");

return 0;

}

}

3)Translate and handle exceptions

In exercise 2, if a user input “a+2”, an exception java.lang.NumberFormatException will be thrown out. The exception must be handled.

To handle exception more precisely, we can add a user-defined exception CalculatorException. WhenNumberFormatException is caught, it can be translated toCalculatorException with detailed error message, and be thrown out again. Interface ICalculatorand class AbstractCalculator will throwCalculatorException. Try to catch the exception in class Test.

package calculatorEx;

import java.util.Scanner;

publicclass Calculator

{

publicstaticvoid main(String[] args) throws Calculators

{

ICalculator Calculator;

String expression;

Scanner n=new Scanner(System.in);

expression=n.nextLine();

if (expression.indexOf("+") != -1)

{

Calculator = new Plus();

}

elseif (expression.indexOf("-") != -1)

{

Calculator = new Minus();

}

elseif (expression.indexOf("*") != -1)

{

Calculator = new Multiply();

}

elseif (expression.indexOf("/") != -1)

{

Calculator = new Divide();

}

else

{

Calculator = new Default();

}

System.out.println("Result:"+Calculator.calculates(expression));

}

}

class Calculators extends Exception

{

privatestaticfinallongserialVersionUID = 1L;

privatestaticfinal String Error="There is a CalculatorException!!!";

public Calculators(String msg)

{

super(msg);

}

public Calculators(String msg, Throwable cause)

{

super(msg, cause);

}

public Calculators(Throwable cause)

{

super(cause);

}

public Calculators()

{

super();

}

publicvoid Handle()

{

System.out.println(Error);

}

}

interface ICalculator

{

publicint calculates(String a) throws Calculators;

}

abstractclass AbstractCalculator

{

publicint[] split(String b,String deliString) throws Calculators

{

try

{

int[] n=newint[10];

n[0]=b.indexOf(deliString);

n[1]=b.indexOf(deliString)+1;

int[] m=newint[10];

m[0]=Integer.parseInt(b.substring(0,n[0]));

m[1]=Integer.parseInt(b.substring(n[1]));

returnm;

}

catch(NumberFormatException e1)

{

System.out.println("There is a NumberFormatException!");

System.out.println("Someone is not a number!");

thrownew Calculators();

}

}

}

class Plus extends AbstractCalculator implements ICalculator

{

publicint calculates(String a) throws Calculators

{

try

{

int[] l=split(a,"+");

returnl[0]+l[1];

}

catch(NumberFormatException e1)

{

System.out.println("Plus Error: NumberFormatException!!!");

thrownew Calculators();

}

}

}

class Minus extends AbstractCalculator implements ICalculator

{

publicint calculates(String a) throws Calculators

{

try

{

int[] l=split(a,"-");

returnl[0]-l[1];

}

catch(NumberFormatException e1)

{

System.out.println("Minus Error: NumberFormatException!!!");

thrownew Calculators();

}

}

}

class Multiply extends AbstractCalculator implements ICalculator

{

publicint calculates(String a) throws Calculators

{

try

{

int[] l=split(a,"*");

returnl[0]*l[1];

}

catch(NumberFormatException e1)

{

System.out.println("Multiply Error: NumberFormatException!!!");

thrownew Calculators();

}

}

}

class Divide extends AbstractCalculator implements ICalculator

{

publicint calculates(String a) throws Calculators

{

try

{

int[] l=split(a,"/");

returnl[0]/l[1];

}

catch(NumberFormatException e1)

{

System.out.println("Divide Error: NumberFormatException!!!");

thrownew Calculators();

}

}

}

class Default extends AbstractCalculator implements ICalculator

{

publicint calculates(String a) throws Calculators

{

try

{

System.out.println("Input Error");

return 0;

}

catch(NumberFormatException e1)

{

System.out.println("Default Error: NumberFormatException!!!");

thrownew Calculators();

}

}

}

4)Write a program that draws a fixed circle centered at (100, 60) with radius 50. Whenever a mouse is moved, display the message indicating whether the mouse point is inside the circle, as shown in following figure:

import java.awt.*;

import java.awt.event.*;

import javax.swing.JFrame;

import javax.swing.JPanel;

import javax.swing.event.MouseInputListener;

publicclassDemoextends JFrame

{

public Demo()

{

add(new newPanel());

}

classnewPanelextends JPanel

{

privateintx;

privateinty;

protectedvoid paintComponent(Graphics g)

{

super.paintComponent(g);

g.drawOval(100, 60, 50, 50);

}

}

privateclassMouseHandlerimplements MouseInputListener{

publicvoid mouseDragged(MouseEvent e){

}

publicvoid mouseMoved(MouseEvent e){

if(find(e.getPoint()))

f.setText("mouse point is in the circle");

else

f.setText(" ");

}

privateboolean find(Point point) {

// TODO Auto-generated method stub

returnfalse;

}

@Override

publicvoid mouseClicked(MouseEvent arg0) {

// TODO Auto-generated method stub

}

@Override

publicvoid mouseEntered(MouseEvent arg0) {

// TODO Auto-generated method stub

}

@Override

publicvoid mouseExited(MouseEvent arg0) {

// TODO Auto-generated method stub

}

@Override

publicvoid mousePressed(MouseEvent arg0) {

// TODO Auto-generated method stub

}

@Override

publicvoid mouseReleased(MouseEvent arg0) {

// TODO Auto-generated method stub

}

}

publicstaticvoid main(String[] args)

{

JFrame f = new Demo();

JFrame p=new JFrame();

f.setTitle("绘制几何图形");

f.setSize(500, 500);

f.setVisible(true);

f.addMouseListener(new MouseAdapter() {

@Override

publicvoid mouseEntered(MouseEvent g)

{

}

});

f.setDefaultCloseOperation(EXIT_ON_CLOSE);

}

}

5)(*****)Write an GUI application that will display a digital clock with a large display panel that shows hour, minute, and second. The numbers must be the same as the system time.

Hints:

1)Query the system time as follows:

GregorianCalendar cal = new GregorianCalendar();

int hour = cal.get(Calendar.HOUR);

int minute = cal.get(Calendar.MINUTE);

int second = cal.get(Calendar.SECOND);

2)Set a timer:

Timer timer = new Timer(1000, new abcdefg());

Class abcdefg implements ActionListener and in its method actionPerformed refresh the numbers showed in application.

3)The schema to show hour, minute, and second is the same. A class DisplayPanel inheriting from JPanel can be create, which contains a JPanel for title and a user-defined JPanel for number.

import javax.swing.JFrame;

import javax.swing.JPanel;

import javax.swing.JLabel;

import java.text.SimpleDateFormat;

import java.util.Date;

import java.awt.*;

publicclass Time extends JFrame implements Runnable

{

privatestaticfinallongserialVersionUID = 1L;

private JLabel time;

private JLabel show;

public Time()

{

this.setVisible(true);

this.setTitle("Alarm Clock");

this.setSize(280, 150);

this.setLocation(200,200);

this.setResizable(true);

JPanel panel = new JPanel();

getContentPane().add(panel, BorderLayout.CENTER);

panel.setLayout(null);

time = new JLabel();

show=new JLabel();

show.setText(" Hour Minute Second");

show.setBounds(0, -20, 300, 100);

show.setFont(new Font("Serif", Font.BOLD, 20));

time.setBounds(31, 34, 196, 100);

time.setFont(new Font("Arial", Font.PLAIN, 50));

panel.add(show);

panel.add(time);

}

publicvoid run()

{

while(true)

{

try

{

time.setText(new SimpleDateFormat("HH mm ss").format(new Date()));

}

catch(Throwable t)

{

t.printStackTrace();

}

}

}

publicstaticvoid main(String[] args)

{

new Thread(new Time()).start();

}

}

4)