【问题标题】:C++ Class of array of objects对象数组的 C++ 类
【发布时间】:2021-12-14 09:27:38
【问题描述】:

我正在学习 C++,为此,我尝试做一个简单的游戏项目(具有与列相同的行和随机分布的数字,从 0-blank 到 rows*rows-1。目标是让玩家将数字更改为按行的数字顺序)。然后 0-blank 可以与任何邻域水平或垂直切换)我通过程序代码对其进行编码,它工作正常。现在我正在尝试使用面向对象的编程和类来重做它。

因此,我有 2 个课程: Number - 存储 2 个位置为 x 和 y 的整数 Deck - 存储数字数组,实际上数组的索引是数字本身,而 Number 对象只存储位置。

甲板甲板(行)创建带有位置的排序数字,并由 std::cout 检查。 现在我正在尝试实现 shuffle 函数,该函数将随机取 2 个数字并切换它们的位置(m_posX 和 m_posY),但是尝试使用相同的原理来获取 m_posX 是不正确的,并且与位置的创建相比,它给出了不同的大数字。 getNumber 只是不能按我的预期工作。 实际上,我需要从 m_game 甲板数组中的确切 Number 对象返回 m_posX 和 m_posY。

欢迎任何建议我做错了什么。

我有这个代码:

Number.h

    #ifndef NUMBER_H
    #define NUMBER_H
    #include <array>
    
    class Number
    {
      public:
    //    Number(int x, int y, int d);
        setPosition (int x, int y);
        setPosition (std::array <int,2> &xy );            // std::array [2]
        setDigits (int d);
        switchPosition (Number &c1, Number &c2);
        std::array<int,2> getPosition ();                 // std::array [2]
        int getPositionX ();
        int getPositionY ();
        int getDigits();                                  // int
    
    
      protected:
        int m_posX;
        int m_posY;
        int m_digits;
    };
    
    #endif // NUMBER_H
    

Number.cpp

    Number::setPosition (int x, int y)
    {
      m_posX = x;
      m_posY = y;
    }
    
    Number::setPosition (std::array <int,2> &xy )
    {
      m_posX = xy [0];
      m_posY = xy [1];
    }
    
    Number::setDigits (int d)
    {
      m_digits=d;
    }
    
    Number::switchPosition (Number &c1, Number &c2)
    {
      int tempX {c1.m_posX};
      int tempY {c1.m_posY};
      c1.setPosition (c2.m_posX, c2.m_posY);
      c2.setPosition (tempX, tempY);
    }
    
    std::array<int,2> Number::getPosition ()
    {
      static std::array <int,2> position;
      position [0] = m_posX;
      position [1] = m_posY;
      return position;
    }
    
    int Number::getDigits ()
    {
      return m_digits;
    }
    
    int Number::getPositionX ()
    {
      return m_posX;
    }
    int Number::getPositionY ()
    {
      return m_posY;
    }
    

deck.h

    #ifndef DECK_H
    #define DECK_H
    #include "number.h"
    
    class Deck
    {
      public:
        Deck(int rows=3);
        shuffleDeck (int rows);
        Number & getNumber (int elementNumber);
    
      protected:
        std::array <Number,100> m_game;
    };
    
    #endif // DECK_H

deck.cpp

    #include "deck.h"
    #include "number.h"
    #include "rnd.h"
    #include <iostream>
    
    
    Deck::Deck(int rows)
    {
      std::array <Number,100> m_game;
      for (int j {0}; j < (rows); ++j)
      {
        for (int i {0}; i < (rows); ++i)
        {
          m_game[i+j*rows].setPosition (i,j);
          std::cout << "Number: " << (i+j*rows) << '\t' << "Coordinates: " << '\t' << m_game[i+j*rows].getPosition()[0] <<"," << m_game[i+j*rows].getPosition()[1] << '\n' ;
        };
      };
    
    std::cout << "fc Deck::Deck (int rows) Number10 posX: "<< m_game[10].getPosition()[0] << '\n';
    std::cout << "fc Deck::Deck (int rows) Number10 posY: "<< m_game[10].getPosition()[1] << '\n';
    }
    
    Number & Deck::getNumber (int elementNumber)
    {
      std::cout << "fc Deck::getNumber() Number " << elementNumber << " getPosition X,Y: " << m_game[elementNumber].getPositionX() << "," << m_game[elementNumber].getPositionY() << '\n' ;
      return m_game[elementNumber];
    }
    
    

game.cpp 运行代码

    #include "game.h"
    #include "gmath.h"
    #include "constant.h"
    #include "graphics.h"
    #include "number.h"
    #include "deck.h"
    #include <iostream>
    
    
    int game (int rows)
    {
      int steps = 0;
      Graphics piece {};
      Deck deck(rows);
      Number temp = deck.getNumber(10);
      int tempI = temp.getPosition()[10];
//   
//    THIS DOES NOT WORK GETTING printed large number as 28573728
//    [10] has m_posX set to 2 and m_posY set to 2 by Deck deck (rows);
//
    
      std::cout << "CHECK game.h Number10 positionX: "<< tempI << '\n';
    
      return steps; // for future counting score
    }

【问题讨论】:

  • 您面临运行时或编译时错误?
  • 没有错误。就在功能甲板甲板(行)之后;使用以下方法获取变量 m_posX 和 m_posY 的函数: Number temp = deck.getNumber(10); int tempI = temp.getPosition()[0]; std::cout
  • 这是完整的代码。 “graphics.h”、“gmath.h”已准备好但目前尚未使用,“constant.h”已准备好但暂时未使用。到目前为止,Main 函数只实现了一个调用:game(4) 来用 4 行初始化游戏本身。

标签: c++ arrays class oop c++17


【解决方案1】:

在这里尝试按值而不是按引用返回:

Number & Deck::getNumber (int elementNumber)
{
  std::cout << "fc Deck::getNumber() Number " << elementNumber << " getPosition X,Y: " << m_game[elementNumber].getPositionX() << "," << m_game[elementNumber].getPositionY() << '\n' ;
  return m_game[elementNumber];
}

像这样:

Number Deck::getNumber (int elementNumber)
{
  std::cout << "fc Deck::getNumber() Number " << elementNumber << " getPosition X,Y: " << m_game[elementNumber].getPositionX() << "," << m_game[elementNumber].getPositionY() << '\n' ;
  return m_game[elementNumber];
}

当然不要忘记更改声明:

Number getNumber (int elementNumber);

【讨论】:

  • 我已经尝试过了,但它不起作用。仍然越来越大,如 28573728 和 0
【解决方案2】:

问题很明显。

在函数game 中,您正在编写int tempI = temp.getPosition()[10];

函数getPosition() 返回一个std::array&lt;int, 2&gt;。所以,一个有 2 个元素的数组。一个用于 x 位置,一个用于 y 位置。但是使用[10],您正试图从您的数组(只有 2 个元素)中访问编号为 10 的元素。这是一个越界错误。所以,它会读取一些随机的无意义值并显示出来。这是未定义的行为。

我不确定你有哪个编译器,但在调试模式下,它应该会抛出异常并通知你问题。

改正

int tempx = temp.getPosition()[0];
int temp< = temp.getPosition()[1];

无论如何,您都需要启用 ALL 编译器警告。它做到了,收到了几十条消息。

您定义了许多没有返回类型的函数。为此,您必须使用 void,例如函数setPosition(int x, int y); 必须定义为void setPosition(int x, int y);。以此类推。

同样在Deck 的构造函数中,您正在重新定义并覆盖类甲板中已经定义的数组std::array &lt;Number, 100&gt; m_game;。删除构造函数中的行。

您也可以考虑将std::array &lt;int, 2&gt;&amp; xy 替换为std::pair 或简单的struct,例如:

struct Position{
    int x;
    int y;
};

这样会更直观。 . .

【讨论】:

  • 谢谢,你所有的建议都是好的,现在可以了。将 std::array 替换为 std::pair 或结构,什么是最好的?我用的是std::pair,它比array简单但和struct有关,临时变量存储不是更复杂吗?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-19
  • 2021-08-15
  • 1970-01-01
  • 2012-08-15
  • 1970-01-01
相关资源
最近更新 更多