有没有办法在条件语句中声明对象?

Ram*_*iri 6 c++ if-statement object

流程图

我无法根据用户的选择搞清楚如何正确创建对象.

在程序中,我问用户他们想要成为他们的班级 - 骑士或巫师.我输入'1'或'2'代表骑士和巫师.

我做了一个switch语句,在case 1中,我声明了一个对象Knight,对于Wizard也是如此.

我需要在switch语句之外使用这些对象,但我不能.我试图制作一个'默认'对象,制作'玩家播放器'; 但由于Player类具有纯虚函数,我也不能这样做.

我该如何有效地做到这一点?

这是我到目前为止:

int main()
{
std::string plyrName;
int input;
bool foo = false;

std::cout << "What is your name?\n";
std::cin >> plyrName;
std::cin.ignore(1000, '\n');

std::cout << "\nWelcome, " << plyrName << ". What class would you like to be?\n";
std::cout << "1. Knight.\n2. Wizard.\n";
std::cin >> input;

while (input != 1 && input != 2)
{
    if (foo == true)
        std::cout << "Please enter 1 for Knight and 2 for Wizard.\n";
    if (!(std::cin >> input))
    {
        std::cin.clear();
        std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
        std::cout << "\n";
        std::cout << "Only integers are allowed.\n";
    }
    else
        std::cout << "\n";
    foo = true;
}

switch (input)
{
case 1:
{
    Wizard player;
    break;
}
case 2:
{
    Knight player;
    break;
}
}


std::cout << "\nHere is your player information summary.\n";
std::cout << player.classType();

system("pause");
return 0;
}
Run Code Online (Sandbox Code Playgroud)

我需要在创建之后访问播放器对象,因为我想向用户输出他们选择的类.Knight和Wizard类都有一个输出它的功能.

编辑:我有一个跟进问题.在图中,Knight&Wizard有一个静态变量'特殊攻击名'.如何在main函数中访问此变量?使用unique_ptr的解决方案意味着指针将指向基类Player,因此不允许访问派生类成员,例如静态变量'special attack name'.我的设计有缺陷吗?

Kun*_*uri 6

在你的情况下,因为你想要完成多态,你应该去指针和引用.为什么?我强烈推荐这个美丽的答案.为什么没有指针/引用时多态性不起作用?

那么,你应该选择一个原始指针Player *吗?

在几乎所有场景中,你都应该永远不会选择原始指针,特别是当它指向动态内存时.只是因为任何编程错误或异常都可能导致delete被跳过.

因此,我强烈建议您使用C++ 11中引入的智能指针unique_ptr,shared_ptr它们遵循RAII模式并保证取消初始化.

以下是unique_ptr您的案例中的使用示例.

#include <memory>

using PlayerPtr = std::unique_ptr<Player>;
using KnightPtr = std::unique_ptr<Knight>;
using WizardPtr = std::unique_ptr<Wizard>;

int main()
{
    ...
    PlayerPtr playerPtr = nullptr;

    switch (input) {
        case 1: {
             playerPtr = KnightPtr(new Knight);
        }
        break;

        case 2: {
             playerPtr = WizardPtr(new Wizard);
        }
        break;
    }

    // use playerPtr outside.
}
Run Code Online (Sandbox Code Playgroud)

编辑:

正如HTNW正确指出的那样,你必须选择std::make_unique而不是使用new.但请记住,这是一个C++ 14概念.您必须具有编译器支持.

  • 如果[建议使用std :: make_unique over new](/sf/ask/1579984171/),这个答案会更好,并解释了为什么我们需要使用指针. (3认同)