C++ Class Entanglement

C++ Class Entanglement

本文关键字:Entanglement Class C++      更新时间:2023-10-16

我试图使用两个类的变量作为从类A的变量访问类B的,反之亦然。然而,我想不出一个可能的解决方案。它总是以循环或以下错误结束:

error: invalid use of non-static data member  
下面是代码示例:

Player.h:

  #ifndef _PLAYER_H_
  #define _PLAYER_H_
#include "Segment/Dynamic_Segment.h"
class Attributes_P;
class Attributes_P : public Attributes_DS{
  protected:
  int inv_mcols, inv_mrows;
  public:
  Attributes_P();
  void controls( int MKEY_UP, int MKEY_RIGHT, int MKEY_DOWN, int MKEY_LEFT );
  void inventory( int inv_mcols, int inv_mrows );
};
class Player : public Dynamic_Segment{
  protected:
  int   **inv;
  public:
  int   MKEY_UP, MKEY_RIGHT, MKEY_DOWN, MKEY_LEFT;
  public:
  Player();
  Attributes_P set;
  friend class Core;
  friend class Attributes_P;
};
#endif

Player.cpp:

#include "Segment/Player.h"
Attributes_P::Attributes_P(){};
Player::Player() : Dynamic_Segment(){
  set.inv_mcols = 0;
  set.inv_mrows = 0;
}
void Attributes_P::inventory( int inv_mcols, int inv_mrows ) {
  this->inv_mcols = inv_mcols;
  this->inv_mrows = inv_mrows;
  Player::inv = new int*[this->inv_mcols]; //<--- Error here
  for( int i = 0; i < this->inv_mrows; i++ ) {
    Player::inv[i] = new int[this->inv_mcols]; //<--- Error here
  }
}
void Attributes_P::controls( int MKEY_UP, int MKEY_RIGHT, int MKEY_DOWN, int MKEY_LEFT ) {
  Player::MKEY_UP = MKEY_UP; //<--- Error here
  Player::MKEY_RIGHT = MKEY_RIGHT; //<--- Error here
  Player::MKEY_DOWN = MKEY_DOWN; //<--- Error here
  Player::MKEY_LEFT = MKEY_LEFT; //<--- Error here
}

已经有一段时间了…任何想法都会很感激!

成员

Player::MKEY_UP
Player::MKEY_RIGHT
Player::MKEY_DOWN
Player::MKEY_LEFT

不是static,因此您只能通过类型为Player的对象访问它们,而不能通过类实例访问它们。

假设你创建了2个播放器对象,p1p2。当调用Attributes_P::controls时,应该更改两个对象的哪个成员?p1还是p2 ?

如果你想在Player对象之间共享这些成员,你可以声明这些成员为static,或者传递一个特定的Player对象作为参数并直接访问它的成员。这是逻辑的一部分,选择取决于您希望程序如何工作。

不能访问MKEY_UP, MKEY_RIGHT, MKEY_DOWN, MKEY_LEFT &因为它们是私有的。

将它们设为私有并写入getter/setter!

我认为您的数据可能过于紧密地交织在一起,也许应该只是一个类。类的目的之一是封装数据,这样就不用去摆弄别人的私有数据了。还有其他问题,你正在做什么使用new和数组等。然而…

Attributes_P::inventory中,你试图修改inv,它被声明为Player的成员。但是Attributes_P不知道你指的是哪个玩家。您需要

  1. Player实例传递给inventory函数,或者
  2. player的引用初始化Attributes_P

选项1:

void Attributes_P::inventory(int inv_mcols, int inv_mrows, Player& player) {
    player.inv = ...
}

选项2:

class Player; // needed so compiler understands next few lines refering to Player
class Attributes_P {
    Player& m_player;
public:
    Attributes_P(Player& player) : m_player(player) {
    }
};
class Player {
    Attributes_P m_attributes;
public:
    Player() : m_attributes(*this) { // pass self to Attributes_P constructor
    }
}
void Attributes_P::inventory(int inv_mcols, int inv_mrows) {
    m_player.inv = ...
}