第十一周:类 + 构造 + 析构 + 复制构造

1.CPU类设计

题目:

声明一个CPU类,包含等级(rank)、频率(frequency)、电压(voltage)等私有属性,有两个公有成员函数run、stop。其中,rank为枚举类型CPU_Rank,声明为enum CPU_Rank{P1=1,P2,P3,P4,P5,P6,P7};frequency为单位是MHz的整型数,vlotage为浮点型的电压值。

(1)分别编写不同的Set函数和Get函数修改、获取私有数据成员,例如void SetRank(CPU_Rank cr);CPU_Rank GetRank();

(2)在构造函数、析构函数、Run函数、Stop函数中分别输出对应的提示语句。

(3)请给构造函数的参数分别赋予默认参数值:P1,1000,220.5。

(4)在主函数中调用Run和Stop函数,并观察构造函数和析构函数的调用顺序。

【输入形式】无输入

【输出形式】构造函数里的输出语句、Run成员函数里的输出语句、Stop成员函数里的输出语句、析构函数里的输出语句

【样例输出】

ConstructCPU!

CPU Run!

CPU Stop!

Destruct CPU!

代码:

#include<iostream>
using namespace std;

enum CPU_Rank{
    
    P1 = 1, P2, P3, P4, P5, P6, P7};

class CPU{
    
    
public:
    CPU(CPU_Rank rr = P1, int f = 1000, float v = 220.5);
    void SetRank(CPU_Rank cr);
    void GetRank();
    void run();
    void stop();
    ~CPU();
private:
    enum CPU_Rank r;
    int frequency;
    float vlotage;
};

CPU::CPU(CPU_Rank rr, int f, float v){
    
    
    cout<<"Construct CPU!"<<endl;
}

void CPU::SetRank(CPU_Rank cr){
    
    
    r = cr;
}

void CPU::GetRank(){
    
    
    cout<< r;
}

void CPU::run(){
    
    
    cout<<"CPU Run!"<<endl;
}

void CPU::stop(){
    
    
    cout<<"CPU Stop!"<<endl;
}

CPU::~CPU(){
    
    
    cout<<"Destruct CPU!"<<endl;
}

int main(){
    
    
    CPU a;
    a.run();
    a.stop();
	return 0;
}

2.Date日期类

题目:

定义一个满足如下要求的Date类

(1)用下面的格式输出日期,如void ShowDate();

日/月/年

(2)可执行在某个日期对象上加一天的操作,如void Add();

(3)可设置该对象为一个新的日期,如void SetDate(int,int,int);

【输入形式】输入原始日期以及新的日期

【输出形式】在主函数里调用成员函数执行加一天的操作,然后输出原始日期加一天后的日期,输出设置日期后的新日期

【样例输入】

2018 11 30

2020 2 9

【样例输出】

after add: 1/12/2018

new date: 9/2/2020

【提示】冒号后面有一个空格

代码:

#include<iostream>
using namespace std;

class Date{
    
    
public:
    void Add(int, int, int);
    void SetDate(int, int, int);
    void ShowDate();
private:
    int year, month, day;
};

void Date::Add(int n, int y, int r){
    
    
    year = n;
    month = y;
    day = r;
    if(month == 31 && day == 12){
    
    
        day = 1;
        month = 1;
        year += 1;
    }
    switch(month){
    
    
        case 1:
        case 3:
        case 5:
        case 7:
        case 8:
        case 10:
        case 12:
            if(day == 31){
    
    
                month += 1;
                day = 1;
                break;
            }
            else {
    
    
                day += 1;
				break;
            }
        case 4:
        case 6:
        case 9:
        case 11:
            if(day == 30){
    
    
                month += 1;
                day = 1;
                break;
            }
            else {
    
    
                day += 1;
				break;
            }
    }
    if(month == 2){
    
    
        if(year / 400 == 0 || (year / 4 == 0 && year % 100 != 0)){
    
    
            if(day == 29){
    
    
                month += 1;
                day = 1;
            }
            else day += 1;
        }
        else{
    
    
           if(day == 28){
    
    
                month += 1;
                day = 1;
           }
           else day += 1;
       }
   }
}

void Date::SetDate(int n, int y, int r){
    
    
    year = n;
    month = y;
    day = r;
}

void Date::ShowDate(){
    
    
    cout<<day<<"/"<<month<<"/"<<year<<endl;
}

int main(){
    
    
    int n, y, r;
    cin>>n>>y>>r;
    Date day;
    day.Add(n,y,r);
    cout<<"after add: ";
    day.ShowDate();
    cin>>n>>y>>r;
    day.SetDate(n,y,r);
    cout<<"new date: ";
    day.ShowDate();
    return 0;
}

3.椭圆类的设计

题目:

设计并测试一个名为Ellipse的椭圆类:
(1)其私有数据成员为外切矩形的左上角与右下角两个点的坐标(4个int型数据成员x1,y1,x2,y2)

(2)声明4个公有的成员函数分别访问椭圆的外切矩形的顶点坐标,例如int Getx1();

(3)设计1个构造函数Ellipse(int,int,int,int)对椭圆的外切矩形的顶点坐标赋值

(4)设计1个公有成员函数Area()计算椭圆的面积

【输入形式】在主函数里输入顶点坐标,并声明一个Ellipse类的对象

【输出形式】在主函数里调用该对象的成员函数输出外切矩形的顶点坐标,计算并输出椭圆的面积。

【样例输入】

-3 1 3 -1

【样例输出】

-3 1 3 -1

9.4245

代码:

#include<iostream>
#include<cmath>
#include<iomanip>
#define PI 3.1415
using namespace std;

class Ellipse{
    
    
public:
    Ellipse(int, int, int, int);
    Ellipse(const Ellipse & e){
    
    
        x1 = e.x1;
        y1 = e.y1;
        x2 = e.x2;
        y2 = e.y2;

    }
    int Getx1(){
    
    return x1;}
    int Gety1(){
    
    return y1;}
    int Getx2(){
    
    return x2;}
    int Gety2(){
    
    return y2;}
    float Area();

private:
    int x1, y1, x2, y2;
};

Ellipse::Ellipse(int xx1, int yy1, int xx2, int yy2){
    
    
    x1 = xx1;
    y1 = yy1;
    x2 = xx2;
    y2 = yy2;
}

float Ellipse::Area(){
    
    
    int b = (double)(Gety1() - Gety2()) / 2;
    int a = (double)(Getx1() - Getx2()) / 2;
    float area = fabs(PI * a * b);
    return area;
}
int main(){
    
    
    int x1, y1, x2, y2;
    cin>>x1>>y1>>x2>>y2;
    Ellipse tuoy(x1, y1, x2, y2);
    cout<<tuoy.Getx1()<<" "<<tuoy.Gety1()<<" "<<tuoy.Getx2()<<" "<<tuoy.Gety2()<<endl;
    cout<<setprecision(4)<<fixed<<tuoy.Area();
    return 0;
}

4.椭圆类拷贝构造函数和析构函数

题目:

(1)拷贝(复制)构造函数的实现。在已经完成的“椭圆类——1”的基础上,增加一个拷贝构造函数。函数原型格式:Ellipse(const Ellipse & e);

(2)增加Show()函数,显示椭圆的外切矩形的顶点坐标。

(3)增加一个成员函数Fun(int y),将椭圆外切矩形的左上角和右下角的纵坐标分别加y和减y。

(4)增加析构函数,在析构函数中输出“xigou”以及待析构对象的外切矩形左上角的横纵坐标。

【输入形式】在主函数中输入顶点坐标后创建一个对象,并用该对象作为初始值再创建一个新对象。输入一个值,用于修改新对象的外切矩形的纵坐标。

【输出形式】在主函数里调用这2个对象的Show函数分别输出外切矩形的顶点坐标,调用Area函数分别计算并输出椭圆的面积。接收修改值y后,调用Fun函数修改新对象的纵坐标。重新计算新对象的面积并输出。

【样例输入】

-3 1 3 -1

1

【样例输出】

-3 1 3 -1

-3 1 3 -1

9.4245

9.4245

18.849

xigou -3 2

xigou -3 1

代码:

#include<iostream>
#define PI 3.1415
#include<cmath>
using namespace std;

class Ellipse{
    
    
public:
    Ellipse(int, int, int, int);
    int Getx1(){
    
    return x1;}
    int Gety1(){
    
    return y1;}
    int Getx2(){
    
    return x2;}
    int Gety2(){
    
    return y2;}
    Ellipse(const Ellipse & e);
    void Show(){
    
    cout<<x1<<" "<<y1<<" "<<x2<<" "<<y2<<endl;}
    void Fun(int y);
    float Area();
    ~Ellipse(){
    
    cout<<"xigou "<<x1<<" "<<y1<<endl;}
private:
    int x1, y1, x2, y2;
};

void Ellipse::Fun(int y){
    
    
    y1 += y;
    y2 -= y;
}

Ellipse::Ellipse(const Ellipse & e){
    
    
    x1 = e.x1;
    y1 = e.y1;
    x2 = e.x2;
    y2 = e.y2;
}

Ellipse::Ellipse(int xx1, int yy1, int xx2, int yy2){
    
    
    x1 = xx1;
    y1 = yy1;
    x2 = xx2;
    y2 = yy2;
}

float Ellipse::Area(){
    
    
    int b = (double)(Gety1() - Gety2()) / 2;
    int a = (double)(Getx1() - Getx2()) / 2;
    float area = fabs(PI * a * b);
    return area;
}

int main(){
    
    
    int x1, y1, x2, y2, yy;
    cin>>x1>>y1>>x2>>y2;
    Ellipse tuoy1(x1, y1, x2, y2);
    cout<<tuoy1.Getx1()<<" "<<tuoy1.Gety1()<<" "<<tuoy1.Getx2()<<" "<<tuoy1.Gety2()<<endl;
    tuoy1.Show();
    cout<<tuoy1.Area()<<endl;
    Ellipse tuoy2(tuoy1);
    cout<<tuoy2.Area()<<endl;
    cin>>yy;
    tuoy2.Fun(yy);
    cout<<tuoy2.Area()<<endl;
    return 0;
}

5.Time时间类

题目:

设计一个Time类,并设计多个重载的构造函数,可以设置时间、进行时间的加减运算、按12小时格式和24小时格式输出时间。

【输入形式】无输入

【输出形式】程序运行结果

【样例输入】无

【样例输出】

t2:01:23:34 PM

t2:13:23:34

t1+t2:15:57:34

t1-t2:10:49:34

t3:01:02:03

代码:

#include<iostream>
#include<iomanip>
using namespace std;

class Time
{
    
    
  int hour, minute, second;
public:
  Time(int h, int m, int s = 0);
  Time(int s = 0);
  int SecCalc(){
    
    return(hour * 60 + minute) * 60 + second;}
  void SetTime(int h = 0, int m = 0, int s = 0);
  void print_12();
  void print_24();
  Time Add(Time &a);
  Time Sub(Time &b);
};

Time::Time(int h, int m, int s){
    
    
    hour = h;
    minute = m;
    second = s;
}

Time::Time(int s){
    
    
    hour = s / 3600;
    minute = (s - (hour * 3600)) / 60;
    second = s - (hour * 3600 + minute * 60);
}

void Time::SetTime(int h, int m, int s){
    
    
    hour = h;
    minute = m;
    second = s;
}

void Time::print_12(){
    
    
    if(hour <= 12)
        {
    
    cout<<setw(2)<<setfill('0')<<hour<<":"<<minute<<":"<<second<<" AM";}
    if(hour > 12)
        {
    
    cout<<setw(2)<<setfill('0')<<hour-12<<":"<<minute<<":"<<second<<" PM";}
}

void Time::print_24(){
    
    
    cout<<setw(2)<<setfill('0')<<hour<<":"<<setw(2)<<setfill('0')<<minute<<":"<<setw(2)<<setfill('0')<<second;
}

Time Time::Add(Time &a){
    
    
    Time t3;
    t3.hour = hour;
    t3.minute = minute;
    t3.second = second;
    t3.second += a.second;
    if(t3.second >= 60){
    
    t3.second -= 60; t3.minute += 1;}
    t3.minute += a.minute;
    if(t3.minute >= 60){
    
    t3.minute -= 60; t3.hour += 1;}
    t3.hour += a.hour;
    if(t3.hour >= 24){
    
    t3.hour -= 24;}
    return t3;
}

Time Time::Sub(Time &b){
    
    
    Time t4;
    t4.hour = hour;
    t4.minute = minute;
    t4.second = second;
    if((t4.hour * 60 + t4.minute) * 60 + t4.second >= (b.hour * 60 + b.minute) * 60 + b.second){
    
    
        int a = ((t4.hour * 60 + t4.minute) * 60 + t4.second) - ((b.hour * 60 + b.minute) * 60 + b.second);
        t4.hour = a / 3600;                                     
        t4.minute = (a - (t4.hour * 3600)) / 60;
        t4.second = a - (t4.hour * 3600 + t4.minute * 60);
    }
    else{
    
    
        int c = ((b.hour * 60 + b.minute) * 60 + b.second) - ((t4.hour * 60 + t4.minute) * 60 + t4.second );
        t4.hour = c / 3600;
        t4.minute = (c - (t4.hour * 3600)) / 60;
        t4.second = c - (t4.hour * 3600 + t4.minute * 60);
    }
    return t4;
}
int main()
{
    
    
  Time t1(2, 34), t2, t3(3723);
  t2.SetTime(13, 23, 34);
  cout<<"t2:";
  t2.print_12();
  cout<<endl<<"t2:";
  t2.print_24();
  cout<<"\nt1+t2:";
  t1.Add(t2).print_24();
  cout<<"\nt1-t2:";
  t1.Sub(t2).print_24();
  cout<<endl<<"t3:";
  t3.print_24();
  return 0;
}

6.两点距离(类的组合成员&&冒号语法)

题目:

定义一个坐标点类Point和求两点距离的距离类Distance,在每个类的构造函数函数体里加上cout输出相应的提示语句,以便观察构造函数被调用的顺序。

【样例输入】无输入
【样例输出】

Point’s constructor was called

Point’s constructor was called

Point’s copyConstructor was called

Point’s copyConstructor was called

Point’s copyConstructor was called

Point’s copyConstructor was called

Distance’s constructor was called

Point’s destructor was called

Point’s destructor was called

the distance is:5

Distance’s destructor was called

Point’s destructor was called

Point’s destructor was called

Point’s destructor was called

Point’s destructor was called

代码:

#include<iostream>
#include<cmath>
using namespace std;

class Point{
    
    
public:
    Point(int xx, int yy);
    Point(Point &r);
    int GetX(){
    
    return x;}
    int GetY(){
    
    return y;}
    ~Point(){
    
    cout<<"Point's destructor was called"<<endl;}
private:
    int x, y;
};

Point::Point(int xx, int yy){
    
    
    x = xx;
    y = yy;
    cout<<"Point's constructor was called"<<endl;
}

Point::Point(Point &r){
    
    
    x = r.x;
    y = r.y;
    cout<<"Point's copyConstructor was called"<<endl;
}

class Distance{
    
    
public:
    Distance(Point a, Point b);
    double GetDis(){
    
    return dist;}
    ~Distance(){
    
    cout<<"Distance's destructor was called"<<endl;}
private:
    Point p1, p2;
    double dist;
};

Distance::Distance(Point a,Point b):p1(a), p2(b){
    
     //要用冒号语法对组合类对象初始化;
    cout<<"Distance's constructor was called"<<endl;
    double x = (double)(p1.GetX() - p2.GetX());
    double y = (double)(p1.GetY() - p2.GetY());
    dist = sqrt(x * x + y * y);

} 
int main(){
    
    
    Point myp1(1, 1),myp2(4, 5);
    Distance myd(myp1, myp2);
    cout<<endl;
    cout<<"the distance is:"<<myd.GetDis()<<endl;
    return 0;
}

7.String类(资源空间问题&&深copy&&浅copy)

题目:

自行编写代码完成自己的String类。注意这里的String字符S大写,主要目的是与C++自带的string类相互区分。

class String //请勿修改本类的声明,请实现具体的成员函数。

{

public:

String(const char *str=NULL); //构造函数

String(const String &r); //拷贝构造函数

~String(); //析构函数

private:

char *mydata; //请勿修改数据成员的类型

};

int main() //请勿修改主函数

{

String s1,s2(“hello”);

String s3(s2);

return 0;

}

请在构造函数、拷贝构造函数、析构函数的函数体里添加相应的cout语句,输出对应的提示。

【输入形式】无输入

【输出形式】构造函数、拷贝构造函数和析构函数里的提示语句

【样例输入】无

【样例输出】

gouzao

gouzao hello

kaobei gouzao hello

xigou hello

xigou hello

xigou

代码:

#include<iostream>
#include<string.h>
using namespace std;

class String
{
    
    
public:
    String(const char *str = NULL){
    
    
        if(str == NULL){
    
    
            mydata = NULL;
            cout<<"gouzao"<<endl;
        }
        if(str != NULL){
    
    
            mydata = new char [strlen(str) + 1]; //char[4] 0123
            strcpy(mydata, str); //strcpy其实可以拷贝\0;
            mydata[strlen(str)] = '\0';
            cout<<"gouzao"<<" "<<mydata<<endl;
        }

    }
    String(const String &r){
    
    
        mydata = new char [strlen(r.mydata) + 1];
        strcpy(mydata, r.mydata);
        cout<<"kaobei gouzao"<<" "<<mydata<<endl;
    }
    ~String(){
    
    
        cout<<"xigou"<<" "<<mydata<<endl;
    }
private:
  char *mydata;
};

int main(){
    
    
  String s1, s2("hello");
  String s3(s2);
  return 0;
}

欢迎提问,学弟学妹们加油~

猜你喜欢

转载自blog.csdn.net/qq_51800570/article/details/120901781