The serialization library relies on the existence of a number
of static variables and tables to store information related
to runtime types. Examples are tables which relate exported
names to types and tables which relate base classes to derived
classes. Construction, destruction and usage of these variables
requires consideration of the following issues:
Некоторые статические переменные и постоянные записи данных относятся к другим. Последовательность инициализации не может быть произвольной, но должна быть в правильной последовательности.
Ряд статических переменных не упоминается явно и без особых мер предосторожности будет удален большинством оптимизаторов кода.
Многие из этих переменных создаются шаблонами, и необходимо соблюдать особую осторожность, чтобы убедиться, что они реализованы.
В многопоточной системе возможно, что эти статические переменные будут доступны одновременно отдельными потоками. Это создаст условия расы с непредсказуемым поведением.
This singleton class addresses all of the above issues.
This singleton implementation has the following features:
Любой экземпляр будет построен до того, как будет предпринята попытка получить к нему доступ.
Any instance created with a template is guaranteed to be instantiated.
Regardless of whether or not an instance has been explicitly
referred to, it will not be stripped by the optimizer when the
executable is built in release mode.
All instances are constructed before
main is called
regardless of where they might be referenced within the program.
In a multi-tasking system, this guarantees that there will be no
race conditions during the construction of any instance. No
thread locking is required to guarantee this.
The above implies that any const
instances are thread-safe during the whole program. Again, no
thread locking is required.
If a mutable instance is created, and such an instance is modified
after main is called in a multi-threading system, there exists
the possibility that a race condition will occur. The serialization
library takes care that in the few places where a mutable
singleton is required, it is not altered after
main is called.
For a more general purpose usage, thread locking on this
singleton could easily be implemented. But as the serialization
library didn't require it, it wasn't implemented.
In order to be used as
singleton<T>
, the type T must be default constructable.
It doesn't require static variables - though it may have them.
Since the library guarantees that only one instance of
singleton<T>
exists and all accesss is through the above static interface
functions, common member functions of T become
the functional equivalent of
static functions.
Просто ссылаясь на одиночный экземпляр в любом месте программы, мы гарантируем, что один и только один экземпляр для указанного типаktmapв этом примере] будет существовать на протяжении всей программы. Никакой другой декларации или определения не требуется.
templateclass extended_type_info_typeid : public detail::extended_type_info_typeid_0, public singleton>{класс друзей singleton>;; private: // частный конструктор для ингибирования любого существования, отличного от // статического. Примечание: не все компиляторы поддерживают это!!! extended_type_info_typeid() : details::extended_type_info_typeid_0(){ type_register(typeid(T)); } ~extended_type_info_typeid(){}...};
Это использование позволит использовать более естественный синтаксис:
Опять же, включение одного или нескольких из вышеперечисленных утверждений в любом месте программы гарантирует, что создается и упоминается один и только один экземпляр.
Этот монотон можно безопасно использовать в многопоточных приложениях, если внимательно следовать простому правилу:
Не звоните get_mutable_instance, когда работает более одного потока.Все синглтоны, используемые в библиотеке сериализации, следуют этому правилу. Для того, чтобы помочь обнаружить случайные нарушения этого правила существуют функции блокировки/разблокировки.
В программе, составленной для отладки, любое вызовget_mutable_instance()В то время как библиотека находится в «запертом» состоянии, она будет задерживаться в утверждении. Состояние блокировки однотонного модуля инициализируется как «разблокированное», чтобы разрешить изменение статических переменных до того, как будет названо основное.Замок()иразблокировать()являются «глобальными» в том смысле, что они влияют на ВСЕ одиночки, определенные этим шаблоном. Все испытания сериализации вызываютблокировку()В начале игры. Для программ, составленных в режиме выпуска, эти функции не имеют эффекта.
Статья Serialization - singleton раздела может быть полезна для разработчиков на c++ и boost.
Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.