Russian Qt Forum

Qt => Общие вопросы => Тема начата: itan от Январь 11, 2007, 18:20



Название: QT4: implicitly && explicitly shared
Отправлено: itan от Январь 11, 2007, 18:20
Кто-нибудь мог бы более подробно объяснить чем отличаются механизмы implicitly shared и explicitly shared ? Что об этом надо знать и на что надо обращать внимание при использовании контейнеров QT (4 версии) ?


Название: QT4: implicitly && explicitly shared
Отправлено: Dendy от Январь 11, 2007, 20:44
Implicitly (Неявно) Shared Class - класс с общими данньІми между екземплярами. КаждьІй екземпляр - независимая логическая копия другого екземпляра. Неважно, что указьІвают они на одни и те же данньІе - при попьІтке изменить любой из екземплятов (вьІзвать любой НЕ-const метод) данньІе будут разделеньІ автоматически. Более того, копии можно создавать между потоками (без всяких мутексов), при етом понятия не иметь какие екземплярьІ из каких потоков ссьІлаются на наши данньІе. Считайте, что в потоке создалась абсолютно независимая копия обьекта, затратив при етом НОЛЬ процессорного времени и НОЛЬ оперативной памяти. Более того - любьІе свои данньІе можно сделать Implicitly Shared с помошью QSharedData и QSharedDataPointer. Большинство классов данньІх именно с неявно разделяющимися данньІми (строка, картинка, вариант, все контейнерьІ).

Сложнейшие задачи могут бьІть решеньІ с помошью таких классов тривиально:

Код:
for ( QHashIterator<QString,QVariant> it( hash_from_another_thread ); it.hasNext(); )
  object_from_some_other_thread->do_some( it.next().key() );


Explicitly (ЯвньІй) Shared Class - тоже класс с общими данньІми между екземплярами. Разница в том, что копия обекта не будет независимой. Изменяя один обьект - изменяете все остальньІе что на него ссьІлаются. Фактически ето аналог безопастного указателя на одни и те же данньІе. Пример - узел DOM QDomNode. Присвоив такой узел некоему родителю, вьІ можете отредактировать его значение из любой точки программьІ.

Например, такой код не прокатит с Implicitly Shared классами, зато отлично подходит для Explicitly Shared:
Код:
QDomElement my_element = document.createElement( "elem" );
root_element.appendChild( my_element );
...
my_element.setAttribute( "best_library", "Qt" );


Такой тоже:
Код:
QDomElement my_element = root_element.elementByTagName( "elem" );
my_element.setAttribute( "mfc", "suxx" );


Так как ето фактически указатель - использовать между потоками только с помощью мутексов.

А явньІм он назьІвается потому, что если нужно сделать незаисимую копию - нужно явно вьІзвать соответствующий метод, например QDomNode::cloneNode(). При етом затратится процессорное время и память на создание глубокой копии.