370 likes | 582 Views
Java 语言程序设计. 华 中 师 范 大 学 计算机科学系 王明安. 第五讲 面向对象编程( OOP ). OOP 概念 举例. OOP 概念. OOP(Objective-Oriented Program) 结构化程序设计 Algorithms + Data Structures = Programs OOP Objective(Data Structures)-Oriented 程序由对象组成,算法封装在对象里 对象就是数据结构 每个对象有自己的任务和方法 算法通过对象自己的方法和调用别的对象的方法实现. OOP 概念.
E N D
Java 语言程序设计 华 中 师 范 大 学 计算机科学系 王明安
第五讲 面向对象编程(OOP) • OOP概念 • 举例
OOP概念 • OOP(Objective-Oriented Program) • 结构化程序设计Algorithms + Data Structures = Programs • OOPObjective(Data Structures)-Oriented • 程序由对象组成,算法封装在对象里 • 对象就是数据结构 • 每个对象有自己的任务和方法 • 算法通过对象自己的方法和调用别的对象的方法实现
OOP概念 • 思考对象的时候,需要采用形象思维,而不是程序化的思维。 • 根据问题来描述问题,而不是根据方案。 • 很难很好地设计出对象,只有数量相当少的“专家”能设计出最好的对象,然后让其他人享用。
OOP概念 • “纯粹”的面向对象程序设计方法 • 所有东西都是对象。 • 程序是一大堆对象的组合; • 每个对象都有自己的存储空间,可容纳其他对象。 • 每个对象都有一种类型。 • 同一类所有对象都能接收相同的消息。
OOP概念 • 抽象和建模 • 抽象的目的 • 通过抽象实现简化 • 通过抽象实现概括 • 抽象的方法 • 分级分类进行抽象 • 用抽象的结果来建立模型
OOP概念 • 问题 • 无数的建模方法 • 没有正确的模型,只有较好的 • 不正确的模型 • 充分反映用户需求的模型 • 用户 • 工程师
Java How to Program, fourth Edition • Object-oriented programming (OOP) • Encapsulates(封装)data (attributes) and functions (behavior) into packages called classes • Data and functions closely related • Information hiding • Implementation details are hidden within the classes themselves • Unit of Java programming: the class • A class is like a blueprint– reusable • Objects are instantiated (例示,created) from the class • For example, a house is an instance of a “blueprint class” • C programmers concentrate on functions
Implementing a Time Abstract Data Type with a Class • In our example • Define two classes, Time1 and TimeTest in separate files • Only one public class per file • Class definitions • Never really create definition from scratch • Use extends to inherit(继承) data and methods from base class • Derived class: class that inherits • Every class in Java subclass of Object • Gets useful methods, discussed later • Class body • Delineated by braces { } • Declare instance variables and methods
举例 class 课堂{ class 教室; class 教师; class 学生[]; class 科目; String 上课时间; boolean 课堂状态; ……}
举例 class 教室{ class 房屋; class 讲台; class 黑板; class 桌椅; int 桌椅数; String 编号;} class 多媒体教室 extends 教室{ class 投影机; class 屏幕; class 计算机; class 扩音设备;}
举例 class 教师 extends 人{String 系别;String 职称;……} class 学生 extends 人{ class 成绩; String 系别; String 学号; ……}
举例 class 课堂{课堂(String r_num, String t_name, String obj_name, String c_time) { 多媒体教室 room = new 多媒体教室 ; 教师 teach = new 教师;学生[] student;科目 object = new 科目; room.set编号(r_num); teach.set名字(t_name); student = new 学生[65]; object.set名称(obj_name);上课时间 = c_time; } ……}
举例 main(){课堂 J_class = new 课堂(“7402”, “王明安”, “JAVA”, “401”); ……}
1 // Fig. 26.1: Time1.java 2 // Time1 class definition 3 import java.text.DecimalFormat; // used for number formatting 4 5 // This class maintains the time in 24-hour format 6 public class Time1 extends Object { 7 private int hour; // 0 - 23 8 private int minute; // 0 - 59 9 private int second; // 0 - 59 10 11 // Time1 constructor initializes each instance variable 12 // to zero. Ensures that each Time1 object starts in a 13 // consistent state. 14 public Time1() 15 { 16 setTime( 0, 0, 0 ); 17 } 18 19 // Set a new time value using universal time. Perform 20 // validity checks on the data. Set invalid values to zero. 21 public void setTime( int h, int m, int s ) 22 { 23 hour = ( ( h >= 0 && h < 24 ) ? h : 0 ); 24 minute = ( ( m >= 0 && m < 60 ) ? m : 0 ); 25 second = ( ( s >= 0 && s < 60 ) ? s : 0 ); 26 } 27 28 // Convert to String in universal-time format 29 public String toUniversalString() 30 { 1. import 1.1 Class definition extendsObject 1.2 Constructor (same name as class) 1.3 Method toUniversalString
31 DecimalFormat twoDigits = new DecimalFormat( "00" ); 32 33 return twoDigits.format( hour ) + ":" + 34 twoDigits.format( minute ) + ":" + 35 twoDigits.format( second ); 36 } 37 38 // Convert to String in standard-time format 39 public String toString() 40 { 41 DecimalFormat twoDigits = new DecimalFormat( "00" ); 42 43 return ( ( hour == 12 || hour == 0 ) ? 12 : hour % 12 ) + 44 ":" + twoDigits.format( minute ) + 45 ":" + twoDigits.format( second ) + 46 ( hour < 12 ? " AM" : " PM" ); 47 } 48 } 1.4 "00" signifies two digits to be printed 2. Override toString
60 t.toUniversalString() + 49 // Fig. 26.1: TimeTest.java 61 "\nThe initial standard time is: " + 50 // Class TimeTest to exercise class Time1 51 import javax.swing.JOptionPane; 62 t.toString() + 52 63 "\nImplicit toString() call: " + t; 53 public class TimeTest { 64 54 public static void main( String args[] ) 65 t.setTime( 13, 27, 6 ); 55 { 66 output += "\n\nUniversal time after setTime is: " + 67 t.toUniversalString() + 56 Time1 t = new Time1(); // calls Time1 constructor 68 "\nStandard time after setTime is: " + 57 String output; 58 69 t.toString(); 59 output = "The initial universal time is: " + 70 71 t.setTime( 99, 99, 99 ); // all invalid values 60 t.toUniversalString() + 72 output += "\n\nAfter attempting invalid settings: " + 73 "\nUniversal time: " + t.toUniversalString() + 74 "\nStandard time: " + t.toString(); 75 1. import JOptionPane(no need to import Time1) 2. main 2.1 toString called implicitly to make object of correct type
76 JOptionPane.showMessageDialog( null, output, 77 "Testing Class Time1", 78 JOptionPane.INFORMATION_MESSAGE ); 79 80 System.exit( 0 ); 81 } 82 } Program Output
1 // Fig. 26.3: Time2.java 2 // Time2 class definition 3 package com.deitel.chtp3.ch26; // place Time2 in a package 4 import java.text.DecimalFormat; // used for number formatting 5 6 // This class maintains the time in 24-hour format 7 public class Time2 extends Object { 8 private int hour; // 0 - 23 9 private int minute; // 0 - 59 10 private int second; // 0 - 59 11 12 // Time2 constructor initializes each instance variable 13 // to zero. Ensures that Time object starts in a 14 // consistent state. 15 public Time2() { setTime( 0, 0, 0 ); } 16 17 // Set Methods 18 // Set a new time value using universal time. Perform 19 // validity checks on the data. Set invalid values to zero. 20 public void setTime( int h, int m, int s ) 21 { 22 setHour( h ); // set the hour 23 setMinute( m ); // set the minute 24 setSecond( s ); // set the second 25 } 26 27 // set the hour 28 public void setHour( int h ) 29 { hour = ( ( h >= 0 && h < 24 ) ? h : 0 ); } 30 1. package statement 1.1 import 1.2 Constructor 1.3 Method definitions
31 // set the minute 32 public void setMinute( int m ) 33 { minute = ( ( m >= 0 && m < 60 ) ? m : 0 ); } 34 35 // set the second 36 public void setSecond( int s ) 37 { second = ( ( s >= 0 && s < 60 ) ? s : 0 ); } 38 39 // Get Methods 40 // get the hour 41 public int getHour() { return hour; } 42 43 // get the minute 44 public int getMinute() { return minute; } 45 46 // get the second 47 public int getSecond() { return second; } 48 49 // Convert to String in universal-time format 50 public String toUniversalString() 51 { 52 DecimalFormat twoDigits = new DecimalFormat( "00" ); 53 54 return twoDigits.format( getHour() ) + ":" + 55 twoDigits.format( getMinute() ) + ":" + 56 twoDigits.format( getSecond() ); 57 } 58 59 // Convert to String in standard-time format 60 public String toString() 1.3 Method definitions (notice get and set methods)
61 { 62 DecimalFormat twoDigits = new DecimalFormat( "00" ); 63 64 return ( ( getHour() == 12 || getHour() == 0 ) ? 65 12 : getHour() % 12 ) + ":" + 66 twoDigits.format( getMinute() ) + ":" + 67 twoDigits.format( getSecond() ) + 68 ( getHour() < 12 ? " AM" : " PM" ); 69 } 70 } 1.3 Method definitions
71 // Fig. 26.3: TimeTest.java 91 72 // Demonstrating the Time2 class set and get methods 92 c.setLayout( new FlowLayout() ); 93 hourLabel = new JLabel( "Set Hour" ); 73 import java.awt.*; 74 import java.awt.event.*; 94 hourField = new JTextField( 10 ); 75 import javax.swing.*; 95 hourField.addActionListener( this ); 76 import com.deitel.chtp3.ch26.Time2; 96 c.add( hourLabel ); 97 c.add( hourField ); 77 78 public class TimeTest extends JApplet 98 99 minuteLabel = new JLabel( "Set minute" ); 79 implements ActionListener { 100 minuteField = new JTextField( 10 ); 80 private Time2 t; 81 private JLabel hourLabel, minuteLabel, secondLabel; 82 private JTextField hourField, minuteField, 83 secondField, display; 84 private JButton tickButton; 85 86 public void init() 87 { 88 t = new Time2(); 89 90 Container c = getContentPane(); 1. import (notice package containing Time2) 1.1 implements ActionListener
101 minuteField.addActionListener( this ); 102 c.add( minuteLabel ); 103 c.add( minuteField ); 104 105 secondLabel = new JLabel( "Set Second" ); 106 secondField = new JTextField( 10 ); 107 secondField.addActionListener( this ); 108 c.add( secondLabel ); 109 c.add( secondField ); 110 111 display = new JTextField( 30 ); 112 display.setEditable( false ); 113 c.add( display ); 114 115 tickButton = new JButton( "Add 1 to Second" ); 116 tickButton.addActionListener( this ); 117 c.add( tickButton ); 118 119 updateDisplay(); 120 } 121 122 public void actionPerformed( ActionEvent e ) 123 { 124 if ( e.getSource() == tickButton ) 125 tick(); 126 else if ( e.getSource() == hourField ) { 127 t.setHour( 128 Integer.parseInt( e.getActionCommand() ) ); 129 hourField.setText( "" ); 130 } 2. Define actionPerformed 2.1 Notice e.getSource
131 else if ( e.getSource() == minuteField ) { 132 t.setMinute( 133 Integer.parseInt( e.getActionCommand() ) ); 134 minuteField.setText( "" ); 135 } 136 else if ( e.getSource() == secondField ) { 137 t.setSecond( 138 Integer.parseInt( e.getActionCommand() ) ); 139 secondField.setText( "" ); 140 } 141 142 updateDisplay(); 143 } 144 145 public void updateDisplay() 146 { 147 display.setText( "Hour: " + t.getHour() + 148 "; Minute: " + t.getMinute() + 149 "; Second: " + t.getSecond() ); 150 showStatus( "Standard time is: " + t.toString() + 151 "; Universal time is: " + t.toUniversalString() ); 152 } 153 154 public void tick() 155 { 156 t.setSecond( ( t.getSecond() + 1 ) % 60 ); 157 158 if ( t.getSecond() == 0 ) { 159 t.setMinute( ( t.getMinute() + 1 ) % 60 ); 160 2.2 Method definitions
161 if ( t.getMinute() == 0 ) 162 t.setHour( ( t.getHour() + 1 ) % 24 ); 163 } 164 } 165 } 2.2 Method definitions
Using the this Reference • Each object has a reference to itself • The this reference • Implicitly used to refer to instance variables and methods • Inside methods • If parameter has same name as instance variable • Instance variable hidden • Use this.variableName to explicitly refer to the instance variable • Use variableName to refer to the parameter
1 // Fig. 26.4: ThisTest.java 2 // Using the this reference to refer to 3 // instance variables and methods. 4 import javax.swing.*; 5 import java.text.DecimalFormat; 6 7 public class ThisTest { 8 public static void main( String args[] ) 9 { 10 SimpleTime t = new SimpleTime( 12, 30, 19 ); 11 12 JOptionPane.showMessageDialog( null, t.buildString(), 13 "Demonstrating the \"this\" Reference", 14 JOptionPane.INFORMATION_MESSAGE ); 15 16 System.exit( 0 ); 17 } 18 } 19 20 class SimpleTime { 21 private int hour, minute, second; 22 23 public SimpleTime( int hour, int minute, int second ) 24 { 25 this.hour = hour; 26 this.minute = minute; 27 this.second = second; 28 } 29 30 public String buildString() 1. import 2. main 2.1 Initialize object 2.2 Define class 2.3 Constructor (note use of this)
31 { 32 return "this.toString(): " + this.toString() + 33 "\ntoString(): " + toString() + 34 "\nthis (with implicit toString() call): " + 35 this; 36 } 37 38 public String toString() 39 { 40 DecimalFormat twoDigits = new DecimalFormat( "00" ); 41 42 return twoDigits.format( this.hour ) + ":" + 43 twoDigits.format( this.minute ) + ":" + 44 twoDigits.format( this.second ); 45 } 46 } 2.4 Method definitions (note use of this) Program Output
Finalizers • Memory • Constructors use memory when creating new objects • Automatic garbage collection • When object no longer used, object marked for garbage collection • Garbage collector executes, memory can be reclaimed • Memory leaks less common in Java than in C and C++
Finalizers (II) • finalizer method • In every class, returns resources to system • Performs termination housekeeping on object • Name always finalize • Takes no parameters, returns no value • Defined in class Object as a placeholder • Every class gets a finalize method
Static Class Members • Static variables • Usually, each object gets its own copy of each variable • static class variables shared among all objects of the class • One copy exists for entire class to use • Keyword static • Only have class scope (not global) • static class variables exist even when no objects do • public static members accessed through references or class name and dot operator • private static members accessed through methods • If no objects exist, classname and public static method must be used
Static Class Members (II) • static methods • Can only access class static members • static methods have no this reference • static variables are independent of objects • Method gc • public static method of class System • Suggests garbage collector execute immediately • Can be ignored • Garbage collector not guaranteed to collect objects in a specific order
1 // Fig. 26.5: Employee.java 2 // Declaration of the Employee class. 3 public class Employee extends Object { 4 private String firstName; 5 private String lastName; 6 privatestaticint count; // # of objects in memory 7 8 public Employee( String fName, String lName ) 9 { 10 firstName = fName; 11 lastName = lName; 12 13 ++count; // increment static count of employees 14 System.out.println( "Employee object constructor: " + 15 firstName + " " + lastName ); 16 } 17 18 protectedvoid finalize() 19 { 20 --count; // decrement static count of employees 21 System.out.println( "Employee object finalizer: " + 22 firstName + " " + lastName + 23 "; count = " + count ); 24 } 25 26 public String getFirstName() { return firstName; } 27 28 public String getLastName() { return lastName; } 29 30 public static int getCount() { return count; } 31 } 1. Class definition 1.1 static variable 1.2 Constructor 1.3 Method finalize 1.4 Get methods
32 // Fig. 8.12: EmployeeTest.java 33 // Test Employee class with static class variable, 34 // static class method, and dynamic memory. 35 import javax.swing.*; 36 37 public class EmployeeTest { 38 public static void main( String args[] ) 39 { 40 String output; 41 42 output = "Employees before instantiation: " + 43 Employee.getCount(); 44 45 Employee e1 = new Employee( "Susan", "Baker" ); 46 Employee e2 = new Employee( "Bob", "Jones" ); 47 48 output += "\n\nEmployees after instantiation: " + 49 "\nvia e1.getCount(): " + e1.getCount() + 50 "\nvia e2.getCount(): " + e2.getCount() + 51 "\nvia Employee.getCount(): " + 52 Employee.getCount(); 53 54 output += "\n\nEmployee 1: " + e1.getFirstName() + 55 " " + e1.getLastName() + 56 "\nEmployee 2: " + e2.getFirstName() + 57 " " + e2.getLastName(); 58 59 // mark objects referred to by e1 and e2 60 // for garbage collection 1. Class definition 1.1 Initialize objects
61 e1 = null; 62 e2 = null; 63 64 System.gc(); // suggest that garbage collector be called 65 66 output += "\n\nEmployees after System.gc(): " + 67 Employee.getCount(); 68 69 JOptionPane.showMessageDialog( null, output, 70 "Static Members and Garbage Collection", 71 JOptionPane.INFORMATION_MESSAGE ); 72 System.exit( 0 ); 73 } 74 } 2. System.gc Program Output
课后练习 • 利用整型数组建立堆栈类和队列类 • 堆栈 先进后出属性:堆栈大小,栈顶位置,容器(整型数组) 方法:压栈,出栈,是否空,是否满 • 队列 先进先出属性:队列大小,当前队长,容器(整型数组)方法:出队列,入队列,是否空,是否满