Информация об изменениях

Сообщение Re[14]: Visual C# vs C++. Надо сравнить перспективы. от 09.01.2017 9:39

Изменено 09.01.2017 9:42 lpd

Re[14]: Visual C# vs C++. Надо сравнить перспективы.
Здравствуйте, alex_public, Вы писали:

_>Здравствуйте, lpd, Вы писали:


_>>>
_>>>auto make_object(int p)
_>>>{
_>>>    if(p<0) return big_object();
_>>>    big_object obj(p);
_>>>    prepare(obj);
_>>>    return obj;
_>>>}
_>>>auto obj=make_object(1024);
_>>>


_>Естественно конструктор перемещение. Т.е. банально добавить в класс big_object метод "big_object(big_object&& о) {}" и всё, семантика перемещения заработает для данного классса.


OK, move-конструктор. Тем не менее, я считаю, что с ними слишком запутанные правила. Я бы предпочел, чтобы по вызывающему коду было понятно, что тут move, и не требовалось каждый раз смотреть определение класса.

lpd>>Но ты привел типичный случай, который решается элементарно:

lpd>>
lpd>>big_object *make_object(int p)
lpd>>{
lpd>>    if (p<0) return new big_object;
lpd>>    big_object *obj = new big_object(p);
lpd>>    prepare(obj);
lpd>>    return obj;
lpd>>}
lpd>>big_object *obj=make_object(1024);
lpd>>...
lpd>>delete obj;
lpd>>


_>Ну так и какой код выглядит сложнее и объёмнее, мой или твой? ) Ты же заявлял, что код с применением семантики перемещения существенно усложняется...


Более короткий код не значит простой, кроме того:
lpd>>В случае с move-семантикой вызывающий код получает локальный объект на стеке(?), который обречен быть локальным. В случае с указателем, его можно отдать разным обработчикам.

_>Да, а семантика перемещения как раз полностью решает проблему с передачей этого "локального" объекта куда-то ещё.


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

lpd>>>>Давай конкретно: вот можешь описать случай с примером приложения и объекта, когда (бы) ты использовал move-семантику? хоть один?

_>>>Вообще то там миллион сценариев. Более того, частенько даже древний код можно существенно ускорить без переписывания, если подключить (перекомпилировать с опцией C++11 или старше) ему семантику перемещения. Но если ты хочешь, то я покажу самый банальный пример с явным вызовом:
_>>>
_>>>vector<big_object> vec;
_>>>big_object obj;
_>>>prepare(obj);
_>>>vec.push_back(move(obj));
_>>>

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

_>И именно такой подход существенно убивает производительность, т.к. добавляет лишний уровень косвенности.


Ты что, всерьез заботишься о времени разыменования указателя или cache-miss? оно ничтожно, а в тех очень редких случаях, где играет роль, пишут просто вставки на ассемблере. Или как такой подход убивает производительность?
Большие объекты в векторе лучше не хранить из-за реаллокации при изменении размера и фрагментации после eraseов. Поэтому и в этом случае указатели удобнее.
Так что все еще необходим пример(желательно конкретного приложения), в котором нужна move-семантика.
Re[14]: Visual C# vs C++. Надо сравнить перспективы.
Здравствуйте, alex_public, Вы писали:

_>Здравствуйте, lpd, Вы писали:


_>>>
_>>>auto make_object(int p)
_>>>{
_>>>    if(p<0) return big_object();
_>>>    big_object obj(p);
_>>>    prepare(obj);
_>>>    return obj;
_>>>}
_>>>auto obj=make_object(1024);
_>>>


_>Естественно конструктор перемещение. Т.е. банально добавить в класс big_object метод "big_object(big_object&& о) {}" и всё, семантика перемещения заработает для данного классса.


OK, move-конструктор. Тем не менее, я считаю, что с ними слишком запутанные правила. Я бы предпочел, чтобы по вызывающему коду было понятно, что тут move, и не требовалось каждый раз смотреть определение класса.

lpd>>Но ты привел типичный случай, который решается элементарно:

lpd>>
lpd>>big_object *make_object(int p)
lpd>>{
lpd>>    if (p<0) return new big_object;
lpd>>    big_object *obj = new big_object(p);
lpd>>    prepare(obj);
lpd>>    return obj;
lpd>>}
lpd>>big_object *obj=make_object(1024);
lpd>>...
lpd>>delete obj;
lpd>>


_>Ну так и какой код выглядит сложнее и объёмнее, мой или твой? ) Ты же заявлял, что код с применением семантики перемещения существенно усложняется...


Более короткий код не значит простой, кроме того:
lpd>>В случае с move-семантикой вызывающий код получает локальный объект на стеке(?), который обречен быть локальным. В случае с указателем, его можно отдать разным обработчикам.

_>Да, а семантика перемещения как раз полностью решает проблему с передачей этого "локального" объекта куда-то ещё.


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

lpd>>>>Давай конкретно: вот можешь описать случай с примером приложения и объекта, когда (бы) ты использовал move-семантику? хоть один?

_>>>Вообще то там миллион сценариев. Более того, частенько даже древний код можно существенно ускорить без переписывания, если подключить (перекомпилировать с опцией C++11 или старше) ему семантику перемещения. Но если ты хочешь, то я покажу самый банальный пример с явным вызовом:
_>>>
_>>>vector<big_object> vec;
_>>>big_object obj;
_>>>prepare(obj);
_>>>vec.push_back(move(obj));
_>>>

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

_>И именно такой подход существенно убивает производительность, т.к. добавляет лишний уровень косвенности.


Ты что, всерьез заботишься о времени разыменования указателя? оно ничтожно, а в тех очень редких случаях, где играет роль, пишут просто вставки на ассемблере. Или как такой подход убивает производительность?
Большие объекты в векторе лучше не хранить из-за реаллокации при изменении размера и фрагментации после eraseов. Поэтому и в этом случае указатели удобнее.
Так что все еще необходим пример(желательно конкретного приложения), в котором нужна move-семантика.