【问题标题】:how to fix terminate called after throwing an instance of 'std::logic_error' what(): basic_string::_M_construct null not valid如何在抛出“std::logic_error”what()的实例后调用终止:basic_string::_M_construct null not valid
【发布时间】:2019-10-26 08:59:23
【问题描述】:

我不确定是什么导致了这个问题,我正在创建一个井字游戏,您可以在其中与计算机对战。

我什么都没试过,因为我不知道这个错误是什么意思。

#include <cstdio>
#include <cstdlib>
#include <iostream>
#include <cmath>
#include <time.h>

using namespace std;

void InitializeBoard(int *gameBoard);
void InitializeTurns(int &whosturnisit,int &turnsTaken);
void InitializegameBoard (int *gameBoard);
void DrawScreen (int *gameBoard);
void taketurnplayer(int *gameBoard,int &turnsTaken,int &whosturnisit);
void taketurncomputer(int *gameBoard,int turnsTaken,int whosturnisit);
int checkforwinner(int *gameBoard);
void displayWinner (int &whoWins);


int main()
{
int gameBoard[10];
int whosturnisit, turnsTaken, whoWins;

    InitializeTurns(whosturnisit,turnsTaken);
    InitializegameBoard(gameBoard);
    DrawScreen (gameBoard);

    do
        {
        if (whosturnisit==1)
            taketurnplayer(gameBoard,turnsTaken,whosturnisit);
        else
            taketurncomputer(gameBoard,turnsTaken,whosturnisit);
        DrawScreen(gameBoard);
        whoWins=checkforwinner(gameBoard);
        }while (  (turnsTaken<9) && (whoWins==0) );
    displayWinner(whoWins);
    return 99;
}

void InitializegameBoard (int *gameBoard)
{
    for (int i=0;i<=9;i++)
    gameBoard[i]=0;
return;
}

void InitializeTurns(int &whosturnisit, int &turnsTaken)
{
    string i=0;
    whosturnisit=0;
    turnsTaken=0;
    cin>>i;
    if (i=="yes")
        whosturnisit=1;
    else
        whosturnisit=2;
return;
}

void DrawScreen(int *gameBoard)
{
    system("cls");
    for (int i=1;i<11;i++)
    cout<<gameBoard[i];
return;
}

void taketurnplayer(int *gameBoard,int &turnsTaken,int &whosturnisit)
{
    int x=0;
    do
    {
    cout<<"where would u like to place your x";
    cin>>x;
    }while (gameBoard[x]!=0);
    gameBoard[x]=1;
    whosturnisit=2;
    turnsTaken++;
    return;
}
void taketurncomputer(int*gameBoard, int turnsTaken, int whosturnisit)
{
    int spot=0;
    do
    {
        spot=1+(std::rand()%(9-1+1));
    }while (gameBoard[spot]!=0);
    gameBoard[spot]=2;
    whosturnisit=1;
    turnsTaken++;
    return;
}
checkforwinner (int*gameBoard)
{
    int thewinneris=0;
    if((gameBoard[1]==gameBoard[2])&&(gameBoard[2]==gameBoard[3])&&(gameBoard[3]!=0))
        thewinneris=gameBoard[1];
    else if ((gameBoard[4]==gameBoard[5])&&(gameBoard[5]==gameBoard[6])&&(gameBoard[6]!=0))
        thewinneris=gameBoard[4];
    else if ((gameBoard[7]==gameBoard[8])&&(gameBoard[8]==gameBoard[9])&&(gameBoard[9]!=0))
        thewinneris=gameBoard[7];
    else if ((gameBoard[1]==gameBoard[5])&&(gameBoard[5]==gameBoard[9])&&(gameBoard[9]!=0))
        thewinneris=gameBoard[1];
    else if ((gameBoard[2]==gameBoard[5])&&(gameBoard[5]==gameBoard[8])&&(gameBoard[8]!=0))
        thewinneris=gameBoard[2];
    else if ((gameBoard[1]==gameBoard[4])&&(gameBoard[4]==gameBoard[7])&&(gameBoard[7]!=0))
        thewinneris=gameBoard[1];
    else if ((gameBoard[3]==gameBoard[6])&&(gameBoard[6]==gameBoard[9])&&(gameBoard[9]!=0))
        thewinneris=gameBoard[3];
    else if ((gameBoard[3]==gameBoard[5])&&(gameBoard[5]==gameBoard[7])&&(gameBoard[7]!=0))
        thewinneris=gameBoard[3];
        return thewinneris;
}
void displayWinner(int &whoWins)
{
    cout<<whoWins;
}

视觉的东西还没有完成,但我认为程序现在应该可以运行了。我不断从终端收到的错误是:

在抛出 'std::logic_error' 的实例后调用终止 what(): basic_string::_M_construct null 无效

进程返回 3 (0x3) 执行时间:0.884 s 按任意键继续。

感谢您的帮助!

【问题讨论】:

  • string i=0; 是错误的。它尝试使用NULL 指针初始化std::string,这是非法的。只是不要初始化它,无论如何你都会用用户输入覆盖任何东西:std::string i;
  • 感谢工作。现在一切都好。

标签: c++


【解决方案1】:

TL;DR:

改变

std::string i = 0;

和朋友们来

std::string i;

这将产生空字符串。当你这样做时,考虑给字符串一个有意义的标识符,比如inputyes_no。这在以后调试时可能会有很大帮助,并且描述性代码大大减少了对 cme​​ts 的需求。

问题:

std::string i = 0;

和朋友。

为什么会出现问题:

这是一个初始化,因此调用了构造函数。

std::string 没有可以转换整数的构造函数,但它确实有一个构造函数,可以接收指向字符数组的指针,不幸的是,整数字面量 0 看起来很像 @987654327 的旧定义@指针

#define NULL 0

调用它而不是发出编译器错误。

使用 NULL 指针构造 std::string 几乎是致命的,因此 string 构造函数会捕获它并引发异常。

std::string i = 1;

没有这个问题。编译器立即拒绝它,因为 1 和指针或任何其他可用于初始化 string 的历史等价物之间没有历史等价性。

旁注:

稍后在代码中注意checkforwinner (int*gameBoard)。看起来缺少返回类型。您需要解决此问题,因为程序未按预期运行。

可能会有编译器警告。如果有,请不要忽略警告。它们是抵御逻辑错误的第一道防线,因此如果您想查看更多警告,以便在它们成为难以诊断的运行时问题之前修复它们。查看您的编译器文档以了解如何调高警告级别,然后将其调高LOUD!

【讨论】:

  • 感谢您提供的所有信息,我已修复所有这些信息并使其正常运行,非常感谢!
猜你喜欢
  • 2023-01-17
  • 2019-02-08
  • 2019-06-23
  • 2012-07-27
  • 2022-01-11
  • 2017-04-11
  • 2021-04-04
  • 1970-01-01
  • 2017-12-13
相关资源
最近更新 更多