从静态函数调用非静态变量

Call non-static variable from a static function

我最近开始使用 C++,我偶然发现了一个我似乎无法理解的问题。

class MyClass
{
    bool eventActive = false;

    static bool JoinCommand()
    {
        if (eventActive == true) // eventActive error: "a nonstatic member reference must be relative to a specific object"
        {
           // do something here...
        }
        else
        {

    }
};

我需要 JoinCommand 是静态的,但我还需要使用 eventActive,它需要是非静态的,并且在同一个 [=31] 中被其他函数 used/modified =].因此我不能将 eventActive 设为静态,因为我还需要将其设为常量。

错误: "a nonstatic member reference must be relative to a specific object"

我想我无法创建 MyClass 的新实例。那么我该如何处理呢?或者有什么我不明白/我误解的地方吗?任何帮助将不胜感激。


编辑:

感谢大家帮助我解决这个问题。我完成了我想要实现的目标,但在学习新事物时我偶然发现了另一个与这个问题很接近的问题。

class Command
{
  public:
    const char *       Name;
    uint32             Permission;
    bool (*Handler)(EmpH*, const char* args); // I do not want to change this by adding more arguments
};
class MyClass : public CommandScript
{
 public:
  MyClass() : CommandScript("listscript") { }
  bool isActive = false;
  Command* GetCommands() const
  {
      static Command commandtable[] =
      {
          { "showlist", 3, &DoShowlistCommand } // Maybe handle that differently to fix the problem I've mentioned below?
      };
      return commandtable;
  }
  static bool DoShowlistCommand(EmpH * handler, const char * args)
  {
     // I need to use isActive here for IF statements but I cannot because
     // DoShowlistCommand is static and isActive is not static. 
     // I cannot pass it as a parameter either because I do not want to
     // change the structure of class Command at all

     // Is there a way to do it?
  }
};

如果您确实希望 JoinCommand 是一个静态方法,而 eventActive 是一个非静态成员,您唯一的选择是将对象显式传递给该方法。

class MyClass
{
    bool eventActive = false;

    static bool JoinCommand(MyClass *object)
    {
        if (object->eventActive) // No error, since we are referencing through an object.
        {
           // do something here...
        }
        else
        {
           // Do something else here
        }
    }
};

拥有一个非静态成员变量意味着 MyClass 的每个实例都有一个独立的 eventActive 成员,并且每个实例的值可以不同。第二点意味着像 "MyClass.eventActive" 这样的东西没有任何意义。如果您有两个 MyClass 实例,其中一个的 eventActive 值为 true,另一个为 false,会怎样?你指的是哪个值?如果您正在尝试创建一个只能有一个实例的 class,您可能想看看单例模式。即使在那种情况下,JoinCommand 也必须是非静态的。

class 的静态成员函数根据定义独立于 class 的任何非静态成员的状态。这意味着您可以在没有对象的情况下使用它。

只要你依赖非静态成员,你的函数就必须是非静态的:

class MyClass
{
    bool eventActive = false;
public: 
    bool JoinCommand()           // non static, because 
    {
        if (eventActive == true) // it depends clearly on the state of the object
        { /* do something here... */ }
    }
};

然后您可以按预期调用您的成员函数:

MyClass omc; 
if (omc.JoinCommand()) 
     cout << "Command joined successfully"<<endl;  

如果您仍然有正当理由保持函数静态:

在静态成员函数中访问非静态元素的唯一方法是告诉函数它必须使用哪个对象来访问非静态元素(参数、全局对象等)。正如您所做的那样,取代了 class。

示例:

class MyClass
{
    bool eventActive = false;
public:
    static bool JoinCommand(MyClass& omc)  // example by provding a parameter
    {
        if (omc.eventActive == true)  // access non static of that object
        { /* do something here... */ }
    }
};

你可以这样称呼它:

MyClass obj; 
if (MyClass::JoinCommand(obj))    // a little bit clumsy, isn't it ? 
   ...