1. 程式人生 > >C++螢幕類,矩形類,圓類小練習

C++螢幕類,矩形類,圓類小練習

1

增強Screen類,使之在程式中只能生成一個例項 增強MyRectangle類,新增顏色資訊 建立MyCircle類 在main函式中建立類的例項。(20分)

題目內容:

修改Screen類:

  1. 在Screen類中,將儲存螢幕寬和高的資料域成員改為 static int 型別。

  2. 在Screen類中,新增兩個 string 型別的資料成員 enter 和 leave,並在建構函式中將他們分別初始化為字串“enter screen”和“leave screen”

  3. 在Screen類中,增加一個 Screen* 型別的靜態的私有資料成員 instance;

  4. 在Screen類中,增加一個靜態公有的 getInstance(int width, int height) 函式,該函式返回instance的值。兩個引數均帶有預設值,分別為 640 和 480

  5. 在getInstance函式中,判斷instance的值,若為0,則設定螢幕的高和寬,然後建立一個存放在堆區的Screen物件,將地址儲存在instance中;若instance的值不為0,則返回instance的值

  6. 在getInstance函式中,如果需要建立Screen物件,則校驗寬和高的值;如果寬與高超過1000,或者其它不合理的設定則用cout輸出“invalid screen size”,然後結束程式

  7. 在Screen類中,新增一個deleteInstance()函式(函式型別自行根據main()中的程式碼確定),將getInstance()函式中申請的記憶體歸還給作業系統。

  8. 在Screen類中,新增一個拷貝建構函式;

  9. Screen類的預設建構函式將螢幕寬和高分別設定為640和480

  10. Screen類的所有建構函式均應輸出字串enter的內容並換行

  11. 為screen類新增解構函式,在其中應輸出字串leave的內容並換行

  12. 刪除Screen類中的帶參建構函式

  13. 將Screen類中所有的建構函式都變成 private 成員

  14. 如有必要,則增加或者修改其他資料成員及函式成員,例如資料域成員的getter與setter函式

  15. 不要忘記在類外對Screen類的所有靜態成員進行初始化,否則編譯器會報告連結出錯。

  • 補充說明:現在的Screen類使用了一種【設計模式】,叫做“單例模式”,可以保證在這個程式中只會有一個Screen的例項。

修改MyRectangle類:

  1. 在MyRectangle類中,增加表示顏色的資料域成員;

  2. 在MyRectangle類中,增加函式 setColor(int R, int G, int B);該函式接收三個引數,代表顏色中的Red、Green、Blue分量的大小,該函式將顏色儲存在類的資料域成員中。

  3. MyRectangle類的建構函式1接受4個整型引數

  4. 按照順序,這4整型引數分別為矩形的左上頂點的x、y座標,以及右下頂點的x、y座標。(此處不做座標有效性檢查)

  5. MyRectangle類的預設建構函式將矩形左上角頂點的座標均設定為(10,10),將右下角定點座標設定為(100,100)

  6. MyRectangle類的所有建構函式均將表示顏色的資料成員初始化為白色,也就是RGB三個顏色分量的值均為255

  7. MyRectangle類的所有建構函式均應使用cout輸出字串“myrectangle”並換行

  8. MyRectangle類中應提供setCoordinations()用於設定對角線的左側及右側頂點座標;函式的引數的含義及型別和建構函式1的前4個引數相同。

  9. MyRectangle類的Draw()函式不再檢查座標的有效性,也不輸出關於座標無效的資訊

  10. 在Draw()中用cout輸出: b. 矩形的左上頂點的x、y座標以及矩形的寬度和高度(座標值以及寬高等4個數值間以1個空格分隔)然後換行; c. 矩形的顏色的RGB分量的值,用空格分隔開的三個整數,然後換行

  11. 如有必要,則增加其他資料成員及函式成員

  12. 不要輸出任何未要求輸出的資訊,不然會導致系統扣分。

新增MyCircle類:

  1. 在MyCircle類中,增加表示顏色的資料域成員;

  2. 在MyCircle類中,增加函式 setColor(int R, int G, int B);該函式接收三個引數,代表顏色中的Red、Green、Blue分量的大小,該函式將顏色儲存在類的資料域成員中。

  3. MyCircle類的建構函式1接受3個整型引數

  4. 按照順序,整型引數分別為圓心的x、y座標,以及圓的半徑。(此處不檢查座標及半徑的有效性)

  5. MyCircle類的預設建構函式將圓心的座標設定為(200,200),半徑設定為100

  6. MyCircle類的“建構函式1”與預設建構函式均將表示顏色的資料成員初始化為白色,也就是RGB三個顏色分量的值均為255

  7. 為MyCircle類新增拷貝建構函式

  8. MyCircle類的所有非拷貝建構函式均應使用cout輸出字串“mycircle”並換行

  9. MyCircle類中應提供setCenter(int x, int y)用於設定圓心座標,提供setRadius(int r)用於設定圓的半徑。

  10. 在Draw()中用cout輸出:

  11. a. 螢幕的寬度和高度,以空格分隔,然後換行; b. 圓心的x、y座標以及半徑(座標值以及半徑等3個數值間以1個空格分隔)然後換行; c. 圓的顏色的RGB分量的值,用空格分隔開的三個整數,然後換行

  12. 如有必要,則增加其他資料成員及函式成員

  13. 不要輸出任何未要求輸出的資訊,不然會導致系統扣分。

main() 函式:

需使用如下main()函式(不得更改)

  1. int main() {
  2.   int width, height;
  3.   cin >> width >> height;
  4.   Screen::getInstance(width, height);
  5.   Screen::getInstance();
  6.   int leftX, leftY, rightX, rightY;
  7.   cin >> leftX >> leftY >> rightX >> rightY;
  8.   MyRectangle myRectangle(leftX, leftY, rightX, rightY);
  9.   myRectangle.setColor(0, 0, 0xff);
  10.   myRectangle.Draw();
  11.   int centerX, centerY, radius;
  12.   cin >> centerX >> centerY >> radius;
  13.   MyCircle myCircles[2];
  14.   (myCircles + 1)->setCenter(centerX, centerY);
  15.   myCircles[1].setRadius(radius);
  16.   myCircles[0].Draw();
  17.   myCircles[1].Draw();
  18.   MyCircle myCircle(myCircles[1]);
  19.   myCircle.Draw();
  20.   Screen::deleteInstance();
  21.   cin.get();
  22.   return 0;
  23. }

輸入格式:

空格分隔的整數

輸出格式:

字串或者空格分隔的整數

輸入樣例:

800 600

30 20 300 200

10 10 50

輸出樣例:

invalid screen size

enter screen

leave screen

myrectangle

mycircle

10 300 690 300

255 255 255

---------------------------

第6單元作業預告

第6單元作業,將在本單元作業基礎上,建立基類MyShape,以及MyShape的派生類MyRectangle和MyCircle。

如果你已經完成了本單元作業,可以提前學習類的繼承。

主要學習靜態成員變數,建構函式,解構函式初始化,單例設計模式,解構函式,簡單的構造拷貝函式

#include <iostream>
#include <string>

using namespace std;

class Screen
{
public:
	int getWidth();
	int getHeight();
public:
	static Screen* getInstance(int width, int height);
	void deleteInstance();
	~Screen();
private:
	int width_;
	int height_;
	string enter;
	string leave;
	static Screen* instance;
private:
	void exitWhenInvalidScreen(int width, int height);
	Screen(int width, int height);
	//Screen();
};

int Screen::getWidth()
{
	return width_;
}

int Screen::getHeight()
{
	return height_;
}

Screen* Screen::getInstance(int width = 640, int height = 480)
{

	if (!instance)
	{
		instance = new Screen(width,height);
	}

	return instance;
}

void Screen::deleteInstance()
{
	delete instance;
	instance = 0; 
}

Screen::~Screen()
{
	cout << leave << endl;
}

void Screen::exitWhenInvalidScreen(int width, int height)
{
	if (width <= 0 || height <= 0)
	{
		cout << "invalid screen size";
		exit(0);
	}

	if (width > 1000 || height > 1000)
	{
		cout << "invalid screen size";
		exit(0);
	}
}

/*Screen::Screen() :width_(640), height_(480),
enter("enter screen"),leave("leave screen")
{
	cout << enter << endl;
}*/

Screen::Screen(int width, int height)//將Screen類中的所有建構函式都變成 private 成員
{

	width_ = width;
	height_ = height;
	enter = "enter screen";
	leave = "leave screen";
	cout << enter << endl;
	exitWhenInvalidScreen(width, height);//檢測螢幕的寬與高是否 符合邏輯
}

class MyRectangle 
{
private:
	int x1_, y1_, x2_, y2_;
	int R_, G_, B_;
	Screen* screen_;

	int getWidth() 
	{
		return x2_ - x1_;
	}

	int getHeight() 
	{
		return y2_ - y1_;
	}

public:
	MyRectangle(int x1, int y1, int x2, int y2, Screen* screen):x1_(x1),y1_(y1),x2_(x2),y2_(y2),
		screen_(screen),R_(255),G_(255),B_(255)
	{
		cout << "myrectangle" << endl;
	}

	MyRectangle():x1_(10),y1_(10),x2_(100),y2_(100),screen_(0),
		R_(255),G_(255),B_(255)

	{
		cout << "myrectangle" << endl;
	}

	void setCoordinations(int x1, int y1, int x2, int y2) {
		x1_ = x1;
		y1_ = y1;
		x2_ = x2;
		y2_ = y2;
	}

	void setScreen(Screen& screen) {
		screen_ = &screen;
	}

	void Draw() {
		cout << x1_ << " " << y1_ << " " <<
			getWidth() << " " <<
			getHeight() << endl;

		cout << R_ << " " << G_ << " " << B_ << endl;
	}

	void setColor(int R, int G, int B)
	{
		R_ = R;
		G_ = G;
		B_ = B;
	}

	void showScreen()
	{
		cout << screen_->getWidth() << " " << screen_->getHeight() << endl;
	}
};

class MyCircle
{
public:
	void setColor(int R, int G, int B);
	void setCenter(int x, int y);
	void setRadius(int r);
	void Draw();
	void showScreen();
	void setScreen(Screen& screen);
	MyCircle(int centerX, int centerY, int radius, Screen* screen);
	MyCircle();
	MyCircle(const MyCircle&);
private:
	int Red_;
	int Green_;
	int Blue_;
	Screen* screen_;
	int centerX_;
	int centerY_;
	int radius_;
};

void MyCircle::setColor(int R, int G, int B)
{
	Red_ = R;
	Green_ = G;
	Blue_ = B;
}

void MyCircle::setCenter(int x, int y)
{
	centerX_ = x;
	centerY_ = y;
}

void MyCircle::setRadius(int r)
{
	radius_ = r;
}

void MyCircle::Draw()
{

	cout << centerX_ << " " << centerY_ << " " << radius_ << endl;
	cout << Red_ << " " << Green_ << " " << Blue_ << endl;
}

void MyCircle::showScreen()
{
	cout << screen_->getWidth() << " " << screen_->getHeight() << endl;
}

void MyCircle::setScreen(Screen& screen)
{
	
	screen_ = &screen;
}

MyCircle::MyCircle(int centerX, int centerY, int radius, Screen* screen):centerX_(centerX),centerY_(centerY),
radius_(radius),screen_(screen),Red_(255),Green_(255),Blue_(255)
{

	cout << "mycircle" << endl;
}

MyCircle::MyCircle():centerX_(200),centerY_(200),radius_(100),
Red_(255),Green_(255),Blue_(255)
{

	cout << "mycircle" << endl;
}

//拷貝建構函式
MyCircle::MyCircle(const MyCircle&rCircle):centerX_(rCircle.centerX_),
centerY_(rCircle.centerY_),radius_(rCircle.radius_),Red_(rCircle.Red_),
Green_(rCircle.Green_),Blue_(rCircle.Blue_),screen_(rCircle.screen_)
{
	cout << "copy mycircle" << endl;
}

Screen* Screen::instance;

int main() {
	int width, height;
	cin >> width >> height;

	int leftX, leftY, rightX, rightY;
	cin >> leftX >> leftY >> rightX >> rightY;

	int centerX, centerY, radius;
	cin >> centerX >> centerY >> radius;

	Screen *screen = Screen::getInstance(width, height);

	MyRectangle myRectangle(leftX, leftY, rightX, rightY, screen);
	myRectangle.setColor(0, 0, 0xff);
	myRectangle.showScreen();
	myRectangle.Draw();

	// 構造圓形物件陣列
	//// 第一個元素使用匿名物件(呼叫帶參建構函式)初始化
	//// 第二個元素使用匿名物件(呼叫預設建構函式)初始化
	MyCircle myCircles[2] = { MyCircle(centerX, centerY, radius, screen) };

	// 設定物件陣列中第二個元素的屬性。注意訪問成員函式的不同方法
	(myCircles + 1)->setCenter(centerX + 10, centerY + 20);
	myCircles[1].setRadius(radius + 30);
	(*(myCircles + 1)).setColor(0x00, 0x00, 0x00);
	myCircles[1].setScreen(*screen);

	for (int i = 0; i <= 1; i++) {
		myCircles[i].showScreen();
		(myCircles + i)->Draw();
	}

	// 呼叫拷貝建構函式以myCircles陣列中的第二個元素為模板建立新物件
	MyCircle yourCircle(myCircles[1]);

	yourCircle.showScreen();
	(&yourCircle)->Draw();

	screen->deleteInstance();

#ifdef DEBUG
	std::cin.get();
#endif
	return 0;
}