Когда использовать ключевое слово «static» в классе C ++? - PullRequest
0 голосов
/ 29 апреля 2009

Код

 static void MyClass::ThreadEntryStatic()
 {
    //...
 }

 void MyClass::Begin()
 {
         CreateThread(..,ThreadEntryStatic,..);
 }

В каких условиях мы должны использовать статические в классе?

Ответы [ 6 ]

4 голосов
/ 29 апреля 2009

Ключевое слово static можно использовать в трех местах. Один из них заключается в объявлении структуры / класса, когда этот контекст означает, что метод является методом класса, а не методом экземпляра. Это означает, что этот метод вызывается напрямую, и вам не нужен экземпляр. С помощью этого статического метода вы не можете получить доступ к переменным экземпляра.

В MyClass.h

struct MyClass
{
  static void ThreadEntryStatic();

  void Begin();
};

В MyClass.cpp

void MyClass::ThreadEntryStatic()
{
}

void MyClass::Begin()
{
  CreateThread(.., MyClass::ThreadEntryStatic, ...);
}

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

Третий случай использования статического ключевого слова находится в области действия метода, и значение сохраняется между выполнениями функции (и инициализируется с присваиванием в первый раз).

1 голос
/ 29 апреля 2009

Несколько человек коснулись этого, но static, используемый для внутренней связи, не должен использоваться, вместо этого следует использовать анонимное пространство имен:

namespace
{

void myInternallyLinkedFunction()
{
    // do something
}

int myInternallyLinkedInteger;

class myInternallyLinkedClass
{
public:
    void doSomething();
};

} // anon namespace


void myExternallyLinkedFunction()
{

    ++myInternallyLinkedInteger;
    myInternallyLinkedFunction();
    myInternallyLinkedClass x;
    x.doSomething();
}
1 голос
/ 29 апреля 2009

В качестве конкретного примера,

class Test{
      static void foo();      
};

static void Test::foo(){
    // code here
}

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

class Test{
      static void foo();      
};

void Test::foo(){
    // code here
}
1 голос
/ 29 апреля 2009

Если вы используете статические методы в нескольких потоках, вам нужно очень внимательно следить за синхронизацией кода. По моему мнению, при многопоточном программировании я стараюсь использовать отдельный экземпляр моего объекта или рабочего элемента для каждого потока и вообще избегать любых типов статических или общих данных. Конечно, это не всегда возможно, поэтому многопоточность остается одной из самых сложных областей программирования.

0 голосов
/ 29 апреля 2009

То, что показывает ваш пример, это шаблон "обратного вызова потока функции статического члена". Поскольку функция потока должна иметь сигнатуру WINAPI, она не может быть обычной функцией-членом, только статическим членом. Часто вы передаете это как параметр потока в этот обратный вызов, а затем вызываете реальный член, выполняющий работу потока.

Существует только одно использование статического члена, и есть много разных. Трудно догадаться, какова цель вашего вопроса. Вы решаете какую-то конкретную проблему или вас просто интересуют все возможные варианты использования статических или статических членов-функций?

Более полный пример "статического обратного вызова потока функции-члена":

class MyClass
{

  /// background rendering thread
  int ThreadEntry()
  {
     // do the work here
  }

  /// static member callback "proxy"
  static DWORD WINAPI ThreadEntryStatic(void *param)
  {
    return ((EngineDD9 *)param)->ThreadEntry();
  }

  void SpawnThread()
  {
    CreateThread(.., ThreadEntryStatic, ...);
  }

};
0 голосов
/ 29 апреля 2009

Значение статических переменных сохраняется между вызовами функций. Проверьте эту запись MSDN для примеров. Определение и использование «статических» методов было изложено в ответе Криша

Статика может использоваться при реализации одноэлементных классов, когда вам нужен только один экземпляр класса. Его использование зависит от контекста.

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