РЕДАКТИРОВАТЬ: Мой ответ предполагает, что создаваемый вами синглтон является довольно сложным и имеет многоэтапный процесс создания. Если это просто статические данные, используйте глобальные, как предлагали другие.
Синглтон в Си будет очень странным. , , Я никогда не видел пример «объектно-ориентированного C», который выглядел бы особенно элегантно. Если возможно, подумайте об использовании C ++. C ++ позволяет вам выбирать, какие функции вы хотите использовать, и многие люди просто используют его как «лучший C».
Ниже приведен довольно типичный шаблон для одноразовой инициализации без блокировки. InterlockCompareExchangePtr атомарно меняет новое значение, если предыдущее значение равно нулю. Это защищает, если несколько потоков пытаются создать синглтон одновременно, победит только один. Остальные удалят свой вновь созданный объект.
MyObj* g_singleton; // MyObj is some struct.
MyObj* GetMyObj()
{
MyObj* singleton;
if (g_singleton == NULL)
{
singleton = CreateNewObj();
// Only swap if the existing value is null. If not on Windows,
// use whatever compare and swap your platform provides.
if (InterlockCompareExchangePtr(&g_singleton, singleton, NULL) != NULL)
{
DeleteObj(singleton);
}
}
return g_singleton;
}
DoSomethingWithSingleton(GetMyObj());