第 3 章 类的基础部分 陈哲 副教授 南京航空航天大学 计算机科学与技术学院.

Slides:



Advertisements
Similar presentations
C++语言程序设计教程 第5章 构造数据类型 第6章 C++程序的结构.
Advertisements

第 2 章 初探 C++.
程序设计实习 3月份练习解答
第九讲 类与对象 (I)面向对象基础.
第4章 数组 数组是由一定数目的同类元素顺序排列而成的结构类型数据 一个数组在内存占有一片连续的存储区域 数组名是存储空间的首地址
第八章 类和对象.
C++程序设计 王希 图书馆三楼办公室.
程式設計 博碩文化出版發行.
struct 可以在同一個名稱下擁有多種資料型態。使用struct能讓資料的存取和處理更為靈活。
資料大樓 --談指標與陣列 綠園.
第二章 C# 基础知识.
函數(一) 自訂函數、遞迴函數 綠園.
Chap 18 類別與物件 夫有土者,有大物也。有大物者,不可以物。 物而不物,故能物物。 明乎物物者之非物也,豈獨治天下百姓而已哉!
C++程序设计 第二讲 清华大学软件学院.
Scope & Lifetime 前言 Local Scope Global Functions & Objects
C++语言程序设计 C++语言程序设计 第六章 指针和引用 第十一组 C++语言程序设计.
刘胥影 东南大学计算机学院 面向对象程序设计1 2011~2012第3学期 刘胥影 东南大学计算机学院.
·线性表的定义及ADT ·线性表的顺序存储结构 ·线性表的链接存储结构 · 单向循环链表 · 双链表、双向循环链表 · 一元多项式的加法
第一章 程序的基本结构. 第一章 程序的基本结构 教材及授课结构 本章目标 基本内容 扩展阅读 上机指导 应用举例 习题.
刘胥影 东南大学计算机学院 面向对象程序设计1 2010~2011第3学期 刘胥影 东南大学计算机学院.
類別樣板 Class Template 類似函式樣板 由類別樣板產生的類別稱為類別樣版的實體(instance)
授课老师:龚涛 信息科学与技术学院 2018年3月 教材: 《Visual C++程序员成长攻略》 《C++ Builder程序员成长攻略》
Object-Oriented Programming in C++ 第一章 C++的初步知识
程序设计期末复习 黎金宁
第三章 C++中的C 面向对象程序设计(C++).
第12章 從C到C++語言 12-1 C++語言的基礎 12-2 C++語言的輸出與輸入 12-3 C++語言的動態記憶體配置
前處理指令可以要求前處理器 (preprocessor) 在程式編譯之前,先進行加入其它檔案的內容、文字取代以及選擇性編譯等工作。
2 C++ 的基本語法和使用環境 親自撰寫和執行程式是學好程式語言的不二法門。本章藉由兩個簡單的程式,介紹C++ 程式的基本結構和開發環境,讓初學者能逐漸建立使用C++ 的信心。
程式撰寫流程.
计算机网络讲义 第5章 批量数据处理—数组 一维数组 排序和查找 二维数组 字符串.
第3讲 C++程序控制结构 3.1 顺序结构 3.2 分支结构 3.3 循环结构 3.4 转向控制 3.5 综合案例分析.
C++语言程序设计 第二章 C++简单程序设计.
程序的三种基本结构 if条件分支语句 switch多路开关语句 循环语句 循环嵌套 break,continue和goto语句
谭浩强 编著 中国高等院校计算机基础教育课程体系规划教材 C++程序设计.
C++语言程序设计 第十一章 流类库与输入/输出.
切換Dev c++顯示語言 工具->環境選項(V)->介面->language (Chinese TW)
第三章 链表 单链表 (Singly Linked List) 循环链表 (Circular List) 多项式及其相加
10 多載函數 10.1 多載概論 多載一般函數 多載成員函數 10-3
第14章 输入输出与文件 输入输出是指程序与外部设备交换信息 C++把输入输出看成是一个数据流 输入流:外围设备流向内存的数据
第三章 链表 单链表 循环链表 多项式及其相加 双向链表 稀疏矩阵.
常宝宝 北京大学计算机科学与技术系 数据结构(三) 常宝宝 北京大学计算机科学与技术系
C++大学基础教程 第11章 多态性 北京科技大学 信息基础科学系 2019/4/8 北京科技大学.
第五章 递归与广义表 递归的概念 递归过程与递归工作栈 递归与回溯 广义表.
第二章 基本数据类型及运算 C数据类型概述 基本数据类型 运算符和表达式 混合运算与类型转换 数据的输入输出 顺序程序设计举例.
Chapter 2 & Chapter 3.
程式結構&語法.
C++语言程序设计 C++语言程序设计 第七章 类与对象 第十一组 C++语言程序设计.
C++语言程序设计 C++语言程序设计 第三章 控制语句 第十一组 C++语言程序设计.
第10讲 构造函数和析构函数 构造函数 析构函数 This 指针.
Oop8 function函式.
物件導向程式設計 CH2.
第11章 從C到C++語言 11-1 C++語言的基礎 11-2 C++語言的資料型態與運算子 11-3 C++語言的輸出與輸入
第三章 数据抽象.
字符串 (String) 字符串是 n (  0 ) 个字符的有限序列, 记作 S = “c1c2c3…cn” 其中,S 是串名字
Object-Oriented Programming in C++ 第二章 类和对象
C++程式設計入門 變數與運算子 作者:黃建庭.
C/C++基礎程式設計班 C++: 物件的使用、參考、重載函式 講師:林業峻 CSIE, NTU 3/28, 2015.
第 8 章 标准模板库STL 陈哲 副教授 南京航空航天大学 计算机科学与技术学院.
挑戰C++程式語言 ──第9章 函數.
#include <iostream.h>
C++语言程序设计 C++语言程序设计 第八章 继承 C++语言程序设计.
第 5 章 继承、多态和虚函数 陈哲 副教授 南京航空航天大学 计算机科学与技术学院.
第 4 章 类的高级部分 陈哲 副教授 南京航空航天大学 计算机科学与技术学院.
C++语言程序设计 第十章 C++标准模板库 成都信息工程学院计算机系.
《数据结构与算法设计》第一部分 面向对象的C++程序设计基础.
第2章 文件操作 陈哲 副教授 南京航空航天大学 计算机科学与技术学院.
C++语言程序设计 C++语言程序设计 第十一章 异常处理 C++语言程序设计.
第9章 C++程序设计初步 9.1 C++的特点 9.2 最简单的C++程序 9.3 C++的输入输出 9.4 函数的重载
變數與資料型態  綠園.
第六章 复合数据类型 指针的声明与使用 数组的声明与使用 指针与数组的相互引用 字符串及相关库函数 new与delete
Presentation transcript:

第 3 章 类的基础部分 陈哲 副教授 南京航空航天大学 计算机科学与技术学院

3.1.1 过程化程序设计的缺陷 出现大量的全局变量; 程序复杂: 程序员难以理解成百上千的函数; 程序难以进行修改和扩充。

3.1.2 面向对象程序设计的基本思想 OOP 以对象为中心,把数据和对数据的操作封装在一起 过程化设计是以过程为中心 (函数) 面向对象设计是以对象为中心 Example:

3.2 类的基本概念 类是一种用户自定义类型,声明形式: class 类名 { 变量和函数的声明; …… } ; 例如:

属性 方法 成员变量 float width; float length; float area; 成员函数 setData( ) { ……} calcArea( ) { ……} getWidth( ) { ……} getLength( ){ ……} getArea( ) { ……} 属性 方法

void setData(float, float); void calcArea( ); float getWidth( ); class Rectangle { float width; float length: float area; void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); }; 默认情况下类的成员是私有的,而结构体(struct)中的成员是公有的。

3.2 类的基本概念(续) 为了使类的成员能够在类外面被访问,其成员必须定义为public. Example:

class Rectangle { private: float width; float length: float area; public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); };

class Rectangle { public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); private: float width; float length: float area; };

class Rectangle { private: float width; public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); float length: float area; };

惯例: class class-name { private: declaration; // ... more declarations may follow... public: };

3.3 定义成员函数 类的成员函数的定义与普通函数的定义类似. 成员函数在类之外定义的常规方式: { … } 3.3 定义成员函数 类的成员函数的定义与普通函数的定义类似. 成员函数在类之外定义的常规方式: <返回值类型> <类名> :: <函数名> ( 参数列表 ) { … }

class Rectangle { private: float width; float length: float area; public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); };

void Rectangle::setData(float w, float l ) { width = w; length = l; } float Rectangle::getWidth ( ) return width;

3.4 定义对象 定义对象称为类的实例化 (模具-铸件) Example: Rectangle box; 3.4 定义对象 定义对象称为类的实例化 (模具-铸件) Example: Rectangle box; box.setData(10.0, 12.5); cout << Box.getWidth( ); Rectangle *boxPtr; boxPtr = &box; boxPtr->setData(15, 12);

// Program 3-1 class Rectangle { private: float width; float length; float area; public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); };

// 参数值传递给私有成员变量 void Rectangle::setData( float w, float l ) { width = w; length = l; } // 计算面积 void Rectangle::calcArea( ) { area = width * length;

// 返回私有成员变量width float Rectangle::getWidth( ) { return width; } // 返回私有成员变量 length float Rectangle::getLength( ) return length; // 返回私有成员变量 area float Rectangle::getArea( ) return area;

cin >> wide>> boxLong; box.setData(wide, boxLong); void main( ) { Rectangle box; float wide, boxLong; cout << " 请输入长和宽 ? "; cin >> wide>> boxLong; box.setData(wide, boxLong); box.calcArea( ); cout << "矩形的数据:\n"; cout << "宽: "<< box.getWidth( ) << endl; cout << "长: "<< box.getLength( )<<endl; cout << "面积: "<< box.getArea( )<<endl; } 3-1.cpp

3.4.3 引入私有成员的原因 在OOP程序设计中,对象保护重要的数据不被破坏是一件很重要的事情,它是通过将关键数据声明为私有成员; 3.4.3 引入私有成员的原因 在OOP程序设计中,对象保护重要的数据不被破坏是一件很重要的事情,它是通过将关键数据声明为私有成员; 当一个成员变量被定义为私有时,唯一对它的访问途径就是通过公有的成员函数。

3.5 类的多文件组织 程序的组织方式: 类的声明存储在头文件里 (类的声明文件). 成员函数定义存储在 .cpp文件 (类的实现文件) . 3.5 类的多文件组织 程序的组织方式: 类的声明存储在头文件里 (类的声明文件). 成员函数定义存储在 .cpp文件 (类的实现文件) . 用户程序(使用该类)通过#include包含头文件。 链接时将类的实现文件和用户程序进行链接,从而生成一个完整的程序。

// Contents of Rectang.h #ifndef RECTANGLE_H #define RECTANGLE_H class Rectangle { float width, length , area; public: void setData(float, float); void calcArea( ); float getWidth( ); float getLength( ); float getArea( ); }; #endif 第一个文件

// Contents of rectang.cpp #include "Rectang.h" // 把参数传递给私有成员 void Rectangle::setData(float w, float l) { width = w; length = l; } // 计算面积 void Rectangle::calcArea( ) area = width * length; 为什么需要这行?

// 返回私有成员:width float Rectangle::getWidth( ) { return width; } // 返回私有成员: length float Rectangle::getLength( ) return length; // 返回私有成员:area float Rectangle::getArea( ) return area;

Rectang.h Rectang.cpp 3-2.cpp //主程序 #include "Rectang.h" //不能省略这一行 void main( ) { Rectangle box; float wide, boxLong; cout << " 输入长和宽 ? "; cin >> wide>> boxLong; box.setData(wide, boxLong); box.calcArea( ); cout << "长: "<< box.getLength( )<<endl; cout << "宽: "<< box.getWidth( ) << endl; cout << "面积: "<< box.getArea( )<<endl; } Rectang.h Rectang.cpp 3-2.cpp

3.6 私有函数成员的作用 专门用于内部处理的函数,它们在类的外部不能使用,这些函数为私有的。 3.6 私有函数成员的作用 专门用于内部处理的函数,它们在类的外部不能使用,这些函数为私有的。 私有函数可以被同一个类中的其它函数调用。Example: class Rectangle { private: float width, length , area; void calcArea( ); public: … };

void Rectangle::setData(float w, float l) { width = w; length = l; calcArea( ); } …

3.7 内联函数 函数体出现在类的定义中,就是内联函数 Example:

#ifndef RECTANGLE_H #define RECTANGLE_H class Rectangle{ private: float width , length, area ; public: void setData( float , float ) ; void calculateArea( ) { area = width * length ; } // 内联函数 float getWidth( ) ; float getLength( ) ; float getArea( ) ; } ; inline void Rectangle::setData( float w, float l ) // 内联函数 { width = w ; length = l ; } #endif

3.7 内联函数 内联函数的特点: 函数体要简单. ( no loop, no switch ) 3.7 内联函数 内联函数的特点: 函数体要简单. ( no loop, no switch ) 对于内联函数,不是通过函数调用方式,而是把函数体直接嵌入调用函数中。 内联发生时间:编译时。

3.8 构造函数和析构函数 1. 构造函数是一个函数成员,当定义类对象时,自 动调用该函数对数据成员进行初始化。 3.8 构造函数和析构函数 1. 构造函数是一个函数成员,当定义类对象时,自 动调用该函数对数据成员进行初始化。 2. 析构函数也是一个函数成员,当对象终止时将自动调用该函数进行“善后”处理。

3.8.1 构造函数 构造函数是与类同名的函数成员; 没有返回值类型,也不允许有void; 如果构造函数没有参数,则称为缺省构造函数; 3.8.1 构造函数 构造函数是与类同名的函数成员; 没有返回值类型,也不允许有void; 如果构造函数没有参数,则称为缺省构造函数; 构造函数的作用:在对象被创建时,采用给定的值将对象初始化为一个特定的状态。 在对象创建时,由系统自动调用; 如果程序中未声明,则系统自动产生出一个缺省形式的构造函数; 允许为内联函数、重载函数、带缺省形参值的函数。 给各成员数据赋初值。

class InvoiceItem // 例3-6 { char *desc; int units; public: InvoiceItem( ) { desc = new char [51]; } void setInfo(char *dscr, int un) strcpy(desc, dscr); units = un; } char *getDesc( ) { return desc; } int getUnits( ) { return units; } };

<< stock.getDesc( ) << endl; cout << "库存量: " void main( ) { InvoiceItem stock; stock.setInfo( "鼠标", 20); cout << "库存物品: " << stock.getDesc( ) << endl; cout << "库存量: " << stock.getUnits( ) << endl; } 3-6.cpp 指向对象的指针: InvoiceItem *ptr ; ptr = new InvoiceItem ; // 此时调用构造函数

3.8.2 析构函数 析构函数也与类同名,前面多个波浪号(~) 当一个对象终止时会自动调用析构函数 3.8.2 析构函数 析构函数也与类同名,前面多个波浪号(~) 当一个对象终止时会自动调用析构函数 Example: Program 3-7.

class InvoiceItem { char *desc; int units; public: InvoiceItem( ) { desc = new char[51]; cout<< "构造函数 \n"; } ~InvoiceItem( ) { delete [ ]desc; cout<< "析构函数 \n";

void setInfo(char *dscr, int un) { strcpy(desc, dscr); units = un; } char *getDesc( ) { return desc; } int getUnits( ) { return units; } }; void main( ) { InvoiceItem stock; stock.setInfo( "鼠标", 20); cout << stock.getDesc( ) << endl; cout << stock.getUnits( ) << endl; 3-7.cpp

3.8.2 析构函数 注 意 Delete对象时,将调用析构函数,例如: InvoiceItem *ptr ; 3.8.2 析构函数 Delete对象时,将调用析构函数,例如: InvoiceItem *ptr ; ptr = new InvoiceItem ; delete ptr ; 1. 同构造函数一样,析构函数也没有返回值类型; 2. 析构函数无参数。 3. 一个类只能有一个析构函数。 注 意

3.8.3 带参构造函数 常常需要把某些数据传递给构造函数用于初始化对象成员。 构造函数可以有缺省参数。 Example:

// Contents of sale2.h class Sale { float taxRate , total; public: Sale(float rate ) { taxRate = rate; } void calcSale( float cost) { total = cost +(cost * taxRate); } float getTotal( ) { return total; } };

//Contents of main program void main( ) { Sale cashier( 0.06f ) ; // 6% 税率 float amount ; cout << "请输入销售额: " ; cin >> amount ; cashier.calculateSale( amount ) ; cout << "销售总额是 RMB" ; cout << cashier.getTotal( ) << endl ; }

构造函数可以有缺省参数: class Sale { float taxRate , total; public: Sale( float rate = 0.05f ) taxRate = rate ; } void calcSale( float cost) { total = cost +(cost * taxRate); } float getTotal( ) { return total; } }; 例 3-9

//Contents of main program void main( ) { Sale cashier1 ; // 缺省形参值 Sale cashier2(0.06f ) ; // 指定形参值 float amount ; cout << "请输入销售额: " ; cin >> amount ; cashier1.calculateSale( amount ) ; cashier2.calculateSale( amount ) ; cout << cashier1.getTotal( ) << endl ; cout << cashier2.getTotal( ) << endl ; }

注意 当构造函数没有参数时,称为缺省构造函数; 如果构造函数所有的参数都有缺省值,那么在函 数调用时不需要显式地传递参数,也属于缺省构 造函数。

3.8.4 构造函数应用举例—输入有效的对象 例3-10. 设计一个CharRange类,这种类型的对象允许用户输入一个字符,然后检验该字符是否位于指定范围(例如,‘A’~‘D’)之内。当用户输入的字符超出指定范围时,该对象将显示一个出错信息,并等待用户重新输入一个新字符 。

#include <iostream> #include <cstring> using namespace std; class CharRange { char *errMsg ; // 出错信息 char input ; // 用户输入值 char lower ; // 有效字符的低界 char upper ; // 有效字符的高界 public: CharRange( char , char , const char * ) ; char getChar( ) ; } ;

CharRange::CharRange( char low , char high , const char *str ) { lower = toupper( low ) ; upper = toupper( high ) ; errMsg = new char [ strlen( str) + 1] ; strcpy( errMsg , str ) ; }

char CharRange::getChar( ) { cin.get(input) ; cin.ignore( ) ; input = toupper( input ) ; while( input < lower || input > upper ) cout << errMsg ; } return input ;

const char *Msg="仅接受 J~N字符"; CharRange input( 'J' , 'N' , Msg ) ; int main( ) { const char *Msg="仅接受 J~N字符"; CharRange input( 'J' , 'N' , Msg ) ; while( input.getChar( ) != 'N') ; return 0; } 3-10.cpp

3.8.5 重载构造函数 一个类中可以定义多个构造函数。 Example: 3-11

InvoiceItem( int size = 51) { desc = new char[size]; } class InvoiceItem { char *desc; int units; public: InvoiceItem( int size = 51) { desc = new char[size]; } InvoiceItem(char *d) { desc = new char[strlen(d)+1]; strcpy(desc, d); } ~InvoiceItem( ) { delete [ ]desc; } // 其它方法略 }; void main( ) { InvoiceItem iteml( "ABC"); InvoiceItem item2; } 3-11.cpp

3.8.6 缺省构造函数的表现形式 1. 如果类中没有定义构造函数,系统将提供一个无参构造函数(属缺省构造函数),该函数不实现任何功能。如果用户自定义了一个构造函数 ,那么系统缺省的构造函数将失效。 2. 如果类中定义有无参的构造函数,那么该构造函数也属于缺省的构造函数。 3. 如果类中定义有带参的构造函数,并且所有形参均具有缺省值,那么该构造函数也属于缺省的构造函数。 4. 一个类只能有一个缺省构造函数,否则将产生二义性。 Example: 下面这个例子就错误的定义了构造函数:

illegal class InvoiceItem { char *desc; int units; public: InvoiceItem( ) { desc = new char[80]; } InvoiceItem(int size = 51) { desc = new char[size]; } ~InvoiceItem( ) { delete[ ] desc; } // 其他函数略 }; illegal

3.9 对象数组 创建对象数组时,数组中每个元素(对象)都将调用构造函数。 3.9 对象数组 创建对象数组时,数组中每个元素(对象)都将调用构造函数。 如果没有为数组元素指定显式初始值,数组元素便使用缺省值初始化(调用缺省构造函数)。 当数组中每一个对象被删除时,都要调用一次析构函数。 例3-12

class InvoiceItem { char *desc ; int storage ; public: InvoiceItem( int size = 51) { desc = new char [ size] ; } InvoiceItem( char *d ) { /* 函数代码略*/ } InvoiceItem( char *d , int u) ~InvoiceItem( ) // 析构函数 { delete[ ] desc ; } // 其他函数略 } ;

InvoiceItem Inventory[3] = { InvoiceItem( "ABC", 10), 思考: 三个对象的初始化 void main( ) { InvoiceItem Inventory[3] = { InvoiceItem( "ABC", 10), InvoiceItem( "DEF") }; for( int i = 0 ; i < 3 ; i++ ) cout << Inventory[i].getDesc ( ) <<endl; } 3-12.cpp

3.11 抽象数组类型 C++对数组不进行下标越界检查,程序员很容易在下标上出错,我们可以创建一个具有数组功能的类实现下标越界检查。 Example: 例3-14.

// 构造函数。对list 中的每个元素初始化 IntArray::IntArray( ) { class IntArray { int list[20]; bool isValid(int); public: IntArray( ); bool set(int, int); bool get(int, int& ); }; // 构造函数。对list 中的每个元素初始化 IntArray::IntArray( ) { for(int i = 0; i < 20; i++) list[i] = 0; } 3-14.cpp

// 检验参数 element 是否为有效的下标 bool IntArray::isValid(int element) { bool status = true; if(element < 0 || element > 19) cout << "ERROR: "<< element; cout << "is an invalid subscript.\n"; status = false; } return status;

// set向指定的数组位置存储一个值。 bool IntArray::set(int element, int value) { bool status = false; if(isValid(element)) list[element] = value; status = true; } return status;

// get获得数组中指定位置的值 . bool IntArray::get(int element, int &value) { bool status = false; if(isValid(element)) value = list [element]; status = true; } return status;

void main( ) { IntArray numbers; int val , x ; // 将 1 存储在数组中,同时显示20个'*' for(x = 0 ; x < 20 ; x++ ) if( numbers.set(x, 1 ) ) cout << "* " ; cout << endl;

for(x = 0; x < 20; x++) if(numbers.get(x, val)) cout << val << " " ; cout << endl; // Attempt to store a value outside the bounds. if(numbers.set(50, 3)) cout << "Element 50 successfully set. \n"; }

3.11.2 扩充抽象数组类型 例3-15. 上节讨论的IntArray类包含一个具有20个元素的整形数组成员,可以完成数组下标越界检查。本节扩展如下几个函数成员 linearSearch BinarySearch bubbleSort selectionSort

class IntArray { int list [20]; bool isValid(int); public: IntArray( ); bool set(int, int); bool get(int, int&); int linearSearch(int); int binarySearch(int); void bubbleSort( ); void selectionSort( ); };

// IntArray 类的构造函数 IntArray:: IntArray( ) { for(int i = 0; i < 20; i++) list [i] = 0; } // isValid 函数检验参数是否为有效的下标 bool IntArray::isValid(int element) { if(element < 0 || element > 19) { cout << "ERROR: "<< element; cout << "is an invalid subscript. \n"; return false; } else return true; }

// set 函数,向指定的数组位置存储一个值 bool IntArray::set(int element, int value) { if(isValid(element)) { list[element] = value; return true; } else return false; } // get member function. bool IntArray::get(int element, int &value) if (isValid(element)) { value = list[element];

// linearSearch线形查找函数. int IntArray::linearSearch(int value) { int status = -1; for (int count = 0; count < 20; count++) if (list [count] == value) status = count; break; } return status;

// binarySearch member function. int IntArray::binarySearch(int value) { int first = 0, last = 19, middle ; selectionSort( ) ; // 首先对数组排序 while( first <= last ) { middle = (first + last) / 2 ; if( list[middle] == value ) return middle ; else if( list[middle] > value ) last = middle - 1 ; else first = middle + 1 ; } return -1 ; // 代表未找到指定的元素

// bubbleSort member function. void IntArray::bubbleSort( ) { int temp ; for( int line = 0 ; line < 19 ; line++ ) for( int col = 0 ; col < 19 - line ; col++ ) if( list [ col ] > list [ col + 1 ] ) { temp = list [ col ] ; list [ col ] = list [ col + 1] ; list [ col + 1 ] = temp ; }

// selectionSort member function. void IntArray::selectionSort( ) { int startScan, minIndex, temp ; for( startScan = 0 ; startScan < 19 ; startScan++ ) { minIndex = startScan ; for( int i = startScan + 1 ; i < 20 ; i++ ) if( list [ i ] < list [ minIndex ] ) minIndex = i ; temp=list[minIndex] ; list[minIndex] = list[startScan] ; list[startScan] = temp ; }

int main ( ) { IntArray numbers; int val, x , searchResult; for ( x = 0; x < 20; x++) if (! numbers.set(x, rand( ))) cout << "存储数据出错! \n" ;

cout << "\n下面是随机产生的 20 个数:\n" ; for( x = 0 ; x < 20 ; x++ ) { if(numbers.get(x, val ) ) cout <<setw( 10 )<<val ; if((x+1) % 5 == 0 ) cout << endl ; } cout << "按 Enter 键继续..."<<endl ; cin.get( ) ;

numbers.selectionSort( ) ; cout << "下面是排序后的 20 个数:\n" ; // 显示排序后的 20 个数 for( x = 0 ; x < 20 ; x++ ) { if(numbers.get(x, val ) ) cout <<setw( 10 )<<val ; if((x+1) % 5 == 0 ) cout << endl ; } cout << endl << endl ;

cout << "输入一个数,然后进行查找: " ; cin >> val ; cout << "正在查找,请稍侯 ...\n" ; searchResult = numbers.binarySearch( val ) ; if( searchResult == -1 ) cout << "没找到!\n" ; else { cout << "在排序后,它的下标位置是:" ; cout << searchResult << endl ; } return 0; 3-15.cpp