Может ли конструктор вызываться из статических функций? - PullRequest
2 голосов
/ 02 мая 2011

Прошу прощения, если этот вопрос задавался ранее (я пытался найти его, но тщетно). Я проходил шаблон проектирования Singleton на http://sourcemaking.com/design_patterns/singleton/cpp/1 (код оттуда скопирован)

class GlobalClass
{
    int m_value;
    static GlobalClass *s_instance;
    GlobalClass(int v = 0)
    {
        m_value = v;
    }
  public:
    int get_value()
    {
        return m_value;
    }
    void set_value(int v)
    {
        m_value = v;
    }
    static GlobalClass *instance()
    {
        if (!s_instance)
          s_instance = new GlobalClass;
        return s_instance;
    }
};

// Allocating and initializing GlobalClass's
// static data member.  The pointer is being
// allocated - not the object inself.
GlobalClass *GlobalClass::s_instance = 0;

void foo(void)
{
  GlobalClass::instance()->set_value(1);
  cout << "foo: global_ptr is " << GlobalClass::instance()->get_value() << '\n';
}

void bar(void)
{
  GlobalClass::instance()->set_value(2);
  cout << "bar: global_ptr is " << GlobalClass::instance()->get_value() << '\n';
}

int main()
{
  cout << "main: global_ptr is " << GlobalClass::instance()->get_value() << '\n';
  foo();
  bar();
}

Мой вопрос в строках если (! s_instance) s_instance = новый GlobalClass;

s_instance = new GlobalClass вызовет конструктор, но конструктор не является статическим, и мы вызываем его из статической функции. Как это работает? Является ли конструктор "особенным" в этом отношении?

Спасибо!

Ответы [ 4 ]

4 голосов
/ 02 мая 2011

Вы можете вызвать конструктор из любого места.Если вы не можете вызвать конструктор без экземпляра, как бы вы взяли какие-либо экземпляры?

Возможно, вы вызывали их из простых функций бесчисленное количество раз.Статические функции ничем не отличаются.

1 голос
/ 02 мая 2011

Да, конструктор можно вызывать из статической функции.Конструктор автоматически вызывается компилятором всякий раз, когда создается новый объект.Это облегчает правильную инициализацию учеников.Да В некотором смысле конструктор можно рассматривать как специальную функцию, которую можно вызывать из статической функции.

В приведенном выше коде вы реализуете шаблон проектирования, называемый Singleton.

0 голосов
/ 02 мая 2011

Да,

  • тривиально: используйте new ClassName -> вызовет конструктор (в новом экземпляре ...)
  • нетривиально: размещение нового (полезно только для очень явного типа реализации библиотеки, сценариев)
0 голосов
/ 02 мая 2011

Точка 1: В C ++ нельзя вызывать нестатическую функцию-член внутри статической функции-члена . Причина в том, что в статической функции нет указателя "this" . Конструкторы не являются исключением .

class A
{
public:
    void fun(){};
    static void static_fun()
    {
        // This is illegal because fun() is non-static
        fun();
    }
};

Пункт 2: Вы всегда можете вызывать методы другого объекта, даже если он нестатический !

class A
{
public:
    void fun(){};
    static void static_fun(A& a)
    {
        // Legal here because it's a (different) object..
        a.fun();
    }
};

Заключение

Это не имеет ничего общего с конструктором в вашем коде. Потому что вы создаете другой объект. Вы можете вызывать все его открытые методы, включая его конструктор.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...