オーバーライドの演習(続き)

ベースクラス(cChara型)

戦士、魔法使い、盗賊の基本機能だけを持った抽象クラス
これ自体は、ベースとして使うからインスタンス化はしない(できない)

cChara.h
#pragma once
#include <iostream>
#include <string>
 
class cChara
{
public:
	//メンバ変数
	std::string m_Name;
	int m_strength;
	//コンストラクタ
	cChara()
		:m_Name(""),m_strength(0){}
	cChara(std::string _name,int _strg)
		:m_Name(_name),m_strength(_strg){}
	//getter setter
	std::string getName() { return m_Name; }
	int getStrength() { return m_strength; }
	void setName(std::string _name) { m_Name = _name; }
	void setStrength(int _strength) { m_strength = _strength; }
	//基本機能
	//・名乗る(自己紹介) 表示のみ ↓
	void declare()
	{std::cout << "私は" << m_Name << "であーる!\n";}
	//・戦う(なぐる)
	void beat()
	{std::cout << "なぐります。ディクシ!\n";}
	//・防御(身を守る)
	void defence()
	{std::cout << "守ります。ガクブル!\n";}
	//・逃げる(逃亡)
	void escape()
	{std::cout << "逃げろー!\n";}
 
	//純粋仮想関数 for 特殊攻撃
	virtual void specialAttack() = 0;
};
== cChara.cpp ==
<code cpp>
#include "cChara.h"
//全部インラインにしちゃったからなんもない。。。

戦士型(cWorrior型)

cChara型を引き継ぎ、戦士としての機能を実装されたクラス。
特に、追加機能はない。特殊攻撃も、戦士は特にないので寂しい。
ただし、仮想関数の実装自体は、何もしないという実装を行っている。

cWorrior.h
#pragma once
#include "cChara.h"
class cWarrior :
    public cChara
{
    //メンバの追加が必要なら書く
public:
    //コンストラクタ
    cWarrior()
        :cChara(){}
    cWarrior(std::string _name, int _strength)
        :cChara(_name, _strength) {}
    //戦士は何も特殊攻撃しない。
    void specialAttack() override { return; };
    //あと、拡張したければ続けて書く
};
cWorrior.cpp
#include "cWarrior.h"
 
//特に書くことなくなっちゃった

魔法使い型(cWizard型)

cChara型を引き継ぎ、魔法使いとしての機能を実装されたクラス。
特に、追加機能はない。特殊攻撃は、魔法を放つ(って表示するだけ)

cWizard.h
#pragma once
#include "cChara.h"
class cWizard :
    public cChara
{
    //メンバの追加が必要なら書く
public:
    //コンストラクタ
    cWizard()
        :cChara() {}
    cWizard(std::string _name, int _strength)
        :cChara(_name, _strength) {}
    //魔法使いは魔法を使える。
    //「攻撃魔法じゃー!」と叫んでください
    void specialAttack() override;
    //あと、拡張したければ続けて書く
};
cWizard.cpp
#include "cWizard.h"
 
using std::cout;
 
void cWizard::specialAttack()
{
	cout << "魔法攻撃じゃー!\n";
}

盗賊型(cThief型)

cChara型を引き継ぎ、魔法使いとしての機能を実装されたクラス。
特に、追加機能はない。特殊攻撃は、魔法を放つ(って表示するだけ)

cThief.h
#pragma once
#include "cChara.h"
class cThief :
    public cChara
{
    //メンバの追加が必要なら書く
public:
    //コンストラクタ
    cThief()
        :cChara() {}
    cThief(std::string _name, int _strength)
        :cChara(_name, _strength) {}
    //盗賊はお金を盗める
    //「戦士からお金を盗もうとした!」と表示
    void specialAttack() override;
    //あと、拡張したければ続けて書く
};
cThief.cpp
#include "cThief.h"
using std::cout;
 
void cThief::specialAttack()
{
	cout << "盗賊は戦士からお金を盗もうとした\n";
}

メイン関数(theMain.cpp)

戦士、魔法使い、盗賊のインスタンスを作って呼び出す。
インスタンスは動的に作成しそのアドレスをvectorに追加する。

theMain.cpp
#include <iostream>
#include "cChara.h"
#include "cWarrior.h"
#include "cWizard.h"
#include "cThief.h"
#include <vector>
 
using std::vector;
 
int main()
{
	//cChara myhero;
	//戦士のオブジェクト
	//=cWarriorクラスのインスタンス を生成
	//cWarrior myWorrior("フリオニール", 60);
	//myWorrior.declare();//名乗る!
	//myWorrior.beat();
	//myWorrior.specialAttack();
	////魔法使いのオブジェクト
	//cWizard myMagician("ふじいあきら", 30);
	//myMagician.declare();//名乗る!
	//myMagician.beat();
	//myMagician.specialAttack();
	////盗賊のオブジェクト
	//cThief myThief("ごえもん", 45);
	//myThief.declare();//名乗る!
	//myThief.beat();
	//myThief.specialAttack();
	//戦士のオブジェクト
	//単独の動的確保なら引数付きが呼べるんだよねぇ
	//cChara* myWorrior = new cWarrior("フリオニール", 60);
	//cChara* myMagician = new cWizard("ふじいあきら", 30);
	//cChara* myThief = new cThief("ごえもん", 45);
 
	vector<cChara*> charBox;
	//実体のあるものを追加
	//charBox.push_back(myWorrior);
	//charBox.push_back(myMagician);
	//charBox.push_back(myThief);
	//オブジェクトを生成して、しかも追加
	charBox.emplace_back(new cWarrior("フリオニール", 60));
	charBox.emplace_back(new cWizard("ふじいあきら", 30));
	charBox.emplace_back(new cThief("ごえもん", 45));
	//charBox.size()
	for (int i = 0; i < charBox.size(); i++) {
		charBox[i]->declare();
		charBox[i]->specialAttack();
	}
 
 
 
	return 0;
}

キーボードから、以下のものを入力しキャラ
をvectorに追加していってください。
①キャラの種類 1:戦士 2:魔法使い 3:盗賊
↑これは switch-caseが必要だよね!
②キャラの名前と、強さ
③キャラの種類に0が入力されたらキャラ入力終了
キャラ入力終了したら、全キャラ名乗りを上げ特殊攻撃
を披露する。

#include <iostream>
#include "cChara.h"
#include "cWarrior.h"
#include "cWizard.h"
#include "cThief.h"
#include <vector>
 
using std::vector;
using std::cin;
using std::string;
 
int main()
{
	int c_num;//キャラ番号
	int cstren;
	string cname;
 
	vector<cChara*> heroBox;
	while (true)
	{
		printf("キャラの種類 1:戦士 2:魔法使い 3:盗賊 :");
		cin >> c_num;
		if (c_num == 0)break;
		else
		{
			printf("キャラの名前を入力:");
			cin >> cname;
			printf("キャラのちからを入力:");
			cin >> cstren;
			cChara* p = nullptr;
			switch (c_num)
			{
			case 1:
				p = new cWarrior(cname, cstren);
				break;
			case 2:
				p = new cWizard(cname, cstren);
				break;
			case 3:
				p = new cThief(cname, cstren);
				break;
			default:
				break;
			}
			heroBox.push_back(p);
		}
	}
 
	return 0;
}
	//イテレータ:繰り返しのための変数
	//ただし、ポインタだよ
	//vector<cChara*>::iterator theI;
	//for (auto theI : heroBox)
	//{
	//	theI->declare();
	//}
	//rbegin(),rend()が、逆順
	for (auto theI = heroBox.begin(); theI != heroBox.end(); theI++)
	{
		(*theI)->declare();
	}
  • game-engineer/classes/2021/game-programing-1/second-term/02/02-14-12.txt
  • 最終更新: 4年前
  • by root