抽象基类(ABC),纯虚函数
#ifndef _ACCTABC_H_
#define _ACCTABC_H_
//(*
#include <iostream>
#include <string>
//*)
//Abstract Base Class
class AcctABC
{
private:
std::string fullName;
long acctNum;
double balance; protected:
struct Formatting
{
std::ios_base::fmtflags flag;
std::streamsize pr;
};
const std::string & FullName(void) const {return fullName;}
long AcctNum(void) const {return acctNum;}
Formatting SetFormat(void) const;
void Restore(Formatting & f) const; public:
AcctABC(const std::string & s = "Nullbody", long an = -, double bal = 0.0);
void Deposit(double amt);
virtual void Withdraw(double amt) = ; //pure virtual function
double Balance(void) const {return balance;};
virtual void ViewAcct(void) const = ; //pure virtual function
virtual ~AcctABC() {}
}; //Brass Account Class
class Brass : public AcctABC
{
public:
Brass(const std::string & s = "Nullbody", long an = -, double bal = 0.0) : AcctABC(s, an, bal) {}
virtual void Withdraw(double amt);
virtual void ViewAcct(void) const;
virtual ~Brass() {}
}; //Brass Plus Account Class
class BrassPlus : public AcctABC
{
private:
double maxLoan;
double rate;
double owesBank; public:
BrassPlus(const std::string & s = "Nullbodt", long an = -, double bal = 0.0, double ml = , double r = 0.10);
BrassPlus(const Brass & ba, double ml = , double r = 0.1);
virtual void ViewAcct(void) const;
virtual void Withdraw(double amt);
void ResetMax(double m) {maxLoan = m;}
void ResetRate(double r) {rate = r;}
void ResetOwes(void) {owesBank = ;}
}; #endif
#include <iostream>
#include "acctabc.h"
using std::cout;
using std::ios_base;
using std::endl;
using std::string; //Abstract Base class
AcctABC::AcctABC(const string & s, long an, double bal)
{
fullName = s;
acctNum = an;
balance = bal;
} void AcctABC::Deposit(double amt)
{
if(amt < )
{
cout << "Negative deposit not allowed; deposit is cancelled." << endl;
}
else
{
balance += amt;
}
} void AcctABC::Withdraw(double amt)
{
balance -= amt;
} //protected methods for formatting
AcctABC::Formatting AcctABC::SetFormat(void) const
{
//set up ###.## format
Formatting f;
f.flag = cout.setf(ios_base::fixed, ios_base::floatfield);
f.pr = cout.precision();
return f;
} void AcctABC::Restore(Formatting & f) const
{
cout.setf(f.flag, ios_base::floatfield);
cout.precision(f.pr);
} //Brass methods
void Brass::Withdraw(double amt)
{
if(amt < )
{
cout << "Withdrawal amount must be positive; withdrawal canceled." << endl;
}
else if(amt < Balance())
{
AcctABC::Withdraw(amt);
}
else
{
cout << "Withdrawal amount of $" << amt << " exceeds your balance." << endl << "Withdrawal canceled." << endl;
}
} void Brass::ViewAcct(void) const
{
Formatting f = SetFormat();
cout << "Brass Client: " << FullName() << endl;
cout << "Account Number: " << AcctNum() << endl;
cout << "Balance: $" << Balance() << endl;
Restore(f);
} //BrassPlus Methods
BrassPlus::BrassPlus(const string & s, long an, double bal, double ml, double r) : AcctABC(s, an, bal)
{
maxLoan = ml;
owesBank = 0.0;
rate = r;
} BrassPlus::BrassPlus(const Brass & ba, double ml, double r) : AcctABC(ba)
{
maxLoan = ml;
owesBank = 0.0;
rate = r;
} void BrassPlus::ViewAcct(void) const
{
Formatting f = SetFormat(); cout << "BrassPlus Client: " << FullName() << endl;
cout << "Account Number: " << AcctNum() << endl;
cout << "Balance: $" << Balance() << endl;
cout << "Maxinum loan: $" << maxLoan <<endl;
cout << "Owed to bank: $" << owesBank << endl;
cout.precision();
cout << "Loan Rate: " << * rate << "%\n";
Restore(f);
} void BrassPlus::Withdraw(double amt)
{
Formatting f = SetFormat(); double bal = Balance();
if(amt <= bal)
{
AcctABC::Withdraw(amt);
}
else if(amt <= bal + maxLoan - owesBank)
{
double advance = amt - bal;
owesBank += advance * (1.0 + rate);
cout << "Bank advance: $" << advance * rate << endl;
Deposit(advance);
AcctABC::Withdraw(amt);
}
else
{
cout << "Credit limit exceeded. Transaction cancelled." << endl;
}
Restore(f);
}
#include <iostream>
#include <string>
#include "acctabc.h"
const int CLIENTS = ; int main(void)
{
using std::cin;
using std::cout;
using std::endl; AcctABC * p_clients[CLIENTS];
std::string temp;
long tempnum;
double tempbal;
char kind; for(int i = ; i < CLIENTS; i++)
{
cout << "Enter client's name: ";
getline(cin, temp);
cout << "Enter client's account number: ";
cin >> tempnum;
cout << "Enter opening balance: $";
cin >> tempbal;
cout << "Enter 1 for Brass Account or 2 for BrassPlus Account: "; while(cin >> kind && (kind != '' && kind != ''))
{
cout << "Enter either 1 or 2: ";
} if(kind == '')
{
p_clients[i] = new Brass(temp, tempnum, tempbal);
}
else
{
double tmax, trate;
cout << "Enter the overdraft limit: $";
cin >> tmax;
cout << "Enter the interest rate " << "as a decimal fraction: ";
cin >> trate;
p_clients[i] = new BrassPlus(temp, tempnum, tempbal, tmax, trate);
} while(cin.get() != '\n')
{
continue;
}
}
cout << endl;
for(int i = ; i < CLIENTS; i++)
{
p_clients[i]->ViewAcct();
cout << endl;
} for(int i = ; i < CLIENTS; i++)
{
delete p_clients[i];
}
cout << "DONE.\n"; return ;
}
抽象基类(ABC),纯虚函数的更多相关文章
- C++:抽象基类和纯虚函数的理解
转载地址:http://blog.csdn.net/acs713/article/details/7352440 抽象类是一种特殊的类,它是为了抽象和设计的目的为建立的,它处于继承层次结构的较上层. ...
- (转)(C++)关于抽象基类和纯虚函数
★抽象类:一个类可以抽象出不同的对象来表达一个抽象的概念和通用的接口,这个类不能实例化(创造)对象. ★纯虚函数(pure virtual):在本类里不能有实现(描述功能),实现需要在子类中实现.例: ...
- 4.6 C++抽象基类和纯虚成员函数
参考:http://www.weixueyuan.net/view/6376.html 总结: 在C++中,可以通过抽象基类来实现公共接口 纯虚成员函数没有函数体,只有函数声明,在纯虚函数声明结尾加上 ...
- C++入门经典-例8.9-抽象类,纯虚函数,创建纯虚函数
1:包含有纯虚函数的类称为抽象类,一个抽象类至少具有一个纯虚函数.抽象类只能作为基类派生出的新的子类,而不能在程序中被实例化(即不能说明抽象类的对象),但是可以使用指向抽象类的指针.在程序开发过程中并 ...
- C++基础知识 基类指针、虚函数、多态性、纯虚函数、虚析构
一.基类指针.派生类指针 父类指针可以new一个子类对象 二.虚函数 有没有一个解决方法,使我们只定义一个对象指针,就可以调用父类,以及各个子类的同名函数? 有解决方案,这个对象指针必须是一个父类类型 ...
- OOP2(虚函数/抽象基类/访问控制与继承)
通常情况下,如果我们不适用某个函数,则无需为该函数提供定义.但我们必须为每个虚函数都提供定义而不管它是否被用到了,这因为连编译器也无法确定到底会适用哪个虚函数 对虚函数的调用可能在运行时才被解析: 当 ...
- C++纯虚函数
本文较为深入的分析了C++中虚函数与纯虚函数的用法,对于学习和掌握面向对象程序设计来说是至关重要的.具体内容如下: 首先,面向对象程序设计(object-oriented programming)的核 ...
- c/c++ 基金会(七) 功能覆盖,虚函数,纯虚函数控制
1.功能覆盖 ClassA , ClassB ,其中ClassB继承ClassA 类的定义如下面的: #ifndef _CLASSA_H #define _CLASSA_H #include < ...
- C++ 虚函数 、纯虚函数、接口的实用方法和意义
也许之前我很少写代码,更很少写面向对象的代码,即使有写多半也很容易写回到面向过程的老路上去.在写面向过程的代码的时候,根本不管什么函数重载和覆盖,想到要什么功能就变得法子的换个函数名字,心里想想:反正 ...
随机推荐
- linux(centos)上配置nginx、mysql、php-fpm、redis开机启动<转>
原文 http://levi.cg.am/archives/2925 I.nginx开机启动 在/etc/init.d/目录下创建脚本 1 vi /etc/init.d/nginx 更改脚本权限 1 ...
- Day12 - 堡垒机开发
Python之路,Day12 - 那就做个堡垒机吧 本节内容 项目实战:运维堡垒机开发 前景介绍 到目前为止,很多公司对堡垒机依然不太感冒,其实是没有充分认识到堡垒机在IT管理中的重要作用的,很多 ...
- Camera类
Camera类 使用 Camera 类可从连接到运行 Flash Player 的计算机的摄像头中 捕获视频. 使用 Video 类可在本地监视视频. 使用 NetConnection 和 NetS ...
- codevs 1183 泥泞的道路 (二分+SPFA+差分约束)
/* 二分答案(注意精度) 对于每一个答案 有(s1+s2+s3...)/(t1+t2+t3...)>=ans 时符合条件 这时ans有变大的空间 对于上述不等式如果枚举每一条路显得太暴力 化简 ...
- HTML5 FileAPI读取实例---(一)
在HTML5中,提供了一个关于文件操作的API,通过这个API,对于从web页面上访问本地文件系统的相关处理变得十分简单.到目前为止只有部分浏览器对它提供支持. 1.FileList对象和File对象 ...
- VI文件编辑操作说明
vi Hello.c (回车后就进入,按i或a键开始编辑.要退出按ESC,进入中间模式,按冒号 :后面跟命令):wq (保存并退出):q!(退出不保存)
- Asp.net 主题 【1】
页面中默认的显示样式太朴素,一页一页的设置控件的显示样式效率又太低,主题和皮肤则提供了一种高效的设计方案. 一.添加主题 二.添加皮肤文件(.skin): 在皮肤文件中添加如下代码 <asp ...
- C# static 干货全解析
讲解顺序 背景 静态字段 静态函数 静态方法 疑问解答 背景 static来源 在编写类的时候,有时候需要类里面的某个成员具有唯一性,也就是,对所有的对象都保持只有一个的状态.比如创建个人信息,我们都 ...
- Web学习资源及手册查询整理
入门了解html.css.js.jQuery:http://www.w3school.com.cn/, bootstrap.nodejs.php.jQuery入门:http://www.runoob. ...
- gdb调试 使用心得
1: 对于在应用程序中加入参数进行调试的方法: 直接用 gdb app -p1 -p2 这样进行调试是不行的. 需要像以下这样使用: #gdb app (gdb) r -p1 -p ...