LINUX.ORG.RU

Rust и создание больших массивов

 ,


3

6

Вот этот очень простой код потенциально легко вызовет stack overflow (если нет, то надо просто увеличить 16777216), хотя не должен (мы ведь на самом деле выделяем место в куче в итоге).

#[derive(Copy, Clone)]
pub struct Item {
    a: i32,
    b: i32
}

pub struct Items {
    items: [Item; 16777216]
}

impl Items {
    pub fn new() -> Items {
        Items {
            items: [Item { a: 0, b: 1 }; 16777216]
        }
    }
}

fn foo() -> Box<Items> {
    Box::new(Items::new())
}

Пруф: https://rust.godbolt.org/z/8sWsoKojx

Для Ъ: Массив сначала создаётся на стеке, а только потом выделяется память и происходит memcpy в кучу. Максимальные оптимизации не спасут.

К тому же не забываем про оверхед копирования. Я готов поверить разработчикам Rust, что копирование при создании структур из нескольких сотен байт не создаст заметной просадки, но я верю, что пример выше будет статистически значимо работать медленнее уже на нескольких тысячах элементов, а не обязательно 16 миллионов.

Как принято создавать в Rust такие массивы? unsafe или есть решения получше?

Мне нравится Rust последнее время, сколько я к нему присматриваюсь, но вот такая очевидная мелочь как copy elision не предусмотрена для типа системного языка... Или я просто всё делаю не так и Items::new надо писать как-то иначе?

★★★★★

Последнее исправление: KivApple (всего исправлений: 2)
Ответ на: комментарий от kvpfs

Еслим вам там чего-то показалось, то это не значит, что я что-то целенаправленно копировал, это первое.

Да, конечно не значит. Только в таком случае всё ещё хуже - если ты это не целенаправленно делаешь, значит ты делаешь это подсознательно. Это пять.

Второе - все мы друг на друга влияем, и если некто говорит - «сектант обгадился», то почему я должен намеренно обходить этот оборот? Что тебе понравиться и твоим друзьям растоадептам?

Да, влияем. Но твоя проблема в том, что ты не фильтруешь влияние окружающих на себя, либо делаешь это недостаточно хорошо. Это как идёшь куда-то, вляпался в какашки - и даже оттереть не пытаешься - «все мы наступаем куда-то, в том числе и в какашки».

Я серьёзно, задумайся над этим - именно так люди и попадают в различные лохотроны. Сцарёк здесь ещё лайт-вариантом будет.

Я буду пользоваться тем, что считаю уместным, от царя, принца или от кого другого - без разницы.

Ради бога, кто ж возражает. Только зачем ты мне это рассказываешь? Запрещать тебе что-то я не собираюсь - это забота твоих родителей, а не моя. Но ты же поспорить сюда пришёл(в хорошем смысле этого слова или нет, не важно)? Вот я тебе и сказал, что так спорить у тебя не получится - повторение чужих доводов интереса никакого для окружающих не представляет. А так, да - пользуйся на здоровье.

Ну и третье - странные претензии от людей, которые как школьницы бегут за модой и большими дядями, которые за раст вписались. Ваши адепты прямо говорили: «мелкомягкие за раст, значит и я в этой команде». И теперь мне про собственное мнение рассказывают? Для начала свое заимейте, потом и поговорить можно.

То же самое, только другими словами неоднократно говорил сцарёк, и на это уже множество раз отвечали. Поэтому повторяться не буду.

anonymous
()
Ответ на: комментарий от anonymous

Какой-то сеанс психотерапевта). По-моему это ты за царём следишь без перерыва, раз в состоянии делать такие заключения

То же самое, только другими словами неоднократно говорил сцарёк, и на это уже множество раз отвечали

Поэтому повторяться не буду.

Конечно не надо, смысл что-то там спрашивать у цепного пса, за вас хозяин говорить будет. Вот скажет: «в расте добавим ручной мув, плейсмент нью, исключения, …» и вы все хором будете кукарекать, что это нужно и безопасно.

kvpfs ★★
()
Ответ на: комментарий от kvpfs

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

anonymous
()
Ответ на: комментарий от kvpfs

Какой-то сеанс психотерапевта).

Нет, конечно. Просто воспитание мальца.

По-моему это ты за царём следишь без перерыва, раз в состоянии делать такие заключения

Попытка сохранить лицо, правда неудачная. Ладно, подскажу тебе, в чём твоя ошибка - подставь в диалог вместо сцарька любое другое указание на конкретного человека и ничего не поменяется.

Конечно не надо, смысл что-то там спрашивать у цепного пса, за вас хозяин говорить будет.

Нет, «взять на слабо» и прочие примитивные техники также не работают. Так легко на поводу идут только дети/подростки.

anonymous
()
Ответ на: комментарий от technic93

Вектор это не то.

Святые Герб и Андрей завещали в правиле 76, для С++ «по умолчанию используйте vector».

anonymous
()
Ответ на: комментарий от anonymous

Все кто реально вписывался за Раст, вписались за него задолго до того, как корпорации решили бросить на него свой взор

Безусловно есть идейные, на них всё и держится. Но как и на любой хайповой вещи, много больше «прилипал», которым просто нужно быть в тренде. Несколько псевднонаучных статей с умными словами, серьезные корпорации и вот собственное мнение готово.

kvpfs ★★
()
Ответ на: комментарий от kvpfs

Для такого и в раст мув будет железно. Вообще не в ту степь ушли, если повторить точно пример топикстартера на C++ то и там тоже будет переполнение стека и такое же копирование. Проблема вовсе не в мувах, они практически одинаковые в обоих языках, проблема в том что в раст нет возможности сразу создавать структуры в динамически созданной памяти и нет аналога placement new.

anonymous
()
Ответ на: комментарий от kvpfs

Вообще-то мовнутый объект остаётся валидным

Остается не валидным, а в виде зомби, и не жив и не мертв.

и я могу его использовать как угодно - вызывать size()

Это не можешь, это ub.

что ещё, оператор =.

Это как раз единственное что разрешенно, в расте кстати тоже разрешается.

anonymous
()

Rust и создание больших массивов

Не впадайте в крайности.
Нужны вам БОЛЬШИЕ массивы, разработайте API для работы с ними.

anonymous
()
Ответ на: комментарий от anonymous

Давно уже разработали, в обоих языках и даже называтся одинаково - вектор.

ТС противник использования vector …

anonymous
()
Ответ на: комментарий от anonymous

Остается не валидным, а в виде зомби, и не жив и не мертв. Это не можешь, это ub.

Пруфы есть? Нет там никакого ЮБ, и юзать я объект могу как угодно. Для конструктор вектора (мувателного), даже так говорят:

constexpr vector( vector&& other ) noexcept;

After the move, other is guaranteed to be empty().
kvpfs ★★
()
Ответ на: комментарий от kvpfs

В общем случае стандарт для библиотечных функций говорит

Objects of types defined in the C++ standard library may be moved from ([class.copy]). Move operations may be explicitly specified or implicitly generated. Unless otherwise specified, such moved-from objects shall be placed in a valid but unspecified state.

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

anonymous
()
Ответ на: комментарий от khrundel

Если бы это было важно, добавили бы до 1.0.

Очнись! в расте с момента 1.0 добавили дофига всего очень важного, даже не говоря об асинках.

Вообще, все мы понимаем, что ([T;N], X) не нужен.

Каким сишникам, алё? Если я знаю размер заранее то записать его в константу компиляции очевидно лучше. С точки зрения и выразительности и перформанса. А если бы в расте были нормальные конст-дженерики то и дополнительные проверки можно бы было сделать.

technic93
()
Ответ на: комментарий от anonymous

Но таки никакого ЮБ там нет, так что я могу спокойно дернуть любой метод. Мовнул строку - дернул clear() - вызвал push_back() -> норм, и все эти стоны: «да у него там use after move!» - ерунда.

kvpfs ★★
()
Последнее исправление: kvpfs (всего исправлений: 1)
Ответ на: комментарий от kvpfs

Да если строго ub нет, есть unspecified state, и чтобы не рисковать лучше всего такой объект вовсе не использовать или если использовать то предварительно его инициализировать. Раст хорош тем что неправильное использование просто не скомпилируется.

anonymous
()

Rust и создание больших массивов

См. в сторону Julia, MatLab, …

anonymous
()
Ответ на: комментарий от kvpfs

Но таки никакого ЮБ там нет, так что я могу спокойно дернуть любой метод.

На, дёрни(сегфолт). Я тебе уже говорил - ты плохо знаешь плюсцы.

#include <new>

template<class T> class vec {
T* begin;
T* end;
T* current;
public:
	explicit vec(unsigned c) {
		begin = static_cast<T*>(operator new[](sizeof(T) * c));
		end = begin + c;
		current = begin;
	}
	vec(vec&& rhs) {
		begin = rhs.begin;
		end = rhs.end;
		current = rhs.current;
		rhs.begin = nullptr;
	}
	vec& operator=(vec&& rhs) {
		while (current != begin) (--current)->~T();
		operator delete[](begin);
		begin = rhs.begin;
		end = rhs.end;
		current = rhs.current;
		rhs.begin = nullptr;
		return *this;
	}
	~vec() {
		while (current != begin) (--current)->~T();
		operator delete[](begin);
	}
};

int main() {
	vec<vec<int>> v1(10);
	vec v2 = static_cast<vec<vec<int>>&&>(v1);
	v1 = vec<vec<int>>(5);
}

Т. е. возможность дёргать должна быть явно обеспечена для конкретного типа. По умолчанию ничего там дёрнуть нельзя.

Для тех кто будет вопрошать «зачем так писать»: нет причин писать, например, так:

+    rhs.current = nullptr;

Это в конструктор и оператор=. Т. е. просто лишние действия с целью подстраховать низкоквалифицированных писателей. Которые, к тому же, кричат что безопасность в раст - не безопасность. Забавно.

anonymous
()
Ответ на: комментарий от anonymous

Конечно же

#include <new>

template<class T> class vec {
T* begin;
T* end;
T* current;
public:
	explicit vec(unsigned c) {
		begin = static_cast<T*>(operator new[](sizeof(T) * c));
		end = begin + c;
		current = begin;
	}
	vec(vec&& rhs) {
		begin = rhs.begin;
		end = rhs.end;
		current = rhs.current;
		rhs.begin = nullptr;
		rhs.current = nullptr;
	}
	vec& operator=(vec&& rhs) {
		while (current != begin) (--current)->~T();
		operator delete[](begin);
		begin = rhs.begin;
		end = rhs.end;
		current = rhs.current;
		rhs.begin = nullptr;
		rhs.current = nullptr;
		return *this;
	}
	~vec() {
		while (current != begin) (--current)->~T();
		operator delete[](begin);
	}
	void push_back(const T& i) {
		if (current == end) throw "growing not implemented";
		new(current) T{i};
		++current;
	}
};

int main() {
	vec<int> v1(10);
	vec v2 = static_cast<vec<int>&&>(v1);
	v1.push_back(0);
}

С присвоением не получится, да. Ну и фикс здесь rhs.end = nullptr.

anonymous
()
Ответ на: комментарий от anonymous

На, дёрни(сегфолт).

Это пять. А чего не спрятал внутри деление на ноль?

cout << "enter 6" << endl;
int i;
cin >> i;
int res = 5 / (i - 6);

Прикинь как тут можно плюсовиков в дерьмо тыкнуть.

Я тебе уже говорил - ты плохо знаешь плюсцы.

Я смотрю ты хорошо знаешь, за такой говнокод нужно руки выдрать, посмотри сколько тут дубляжа … Откуда это? С govnokod.ru? Какая-то лаба первокурсницы. Как-то так надо:

template<class T> class vec {
	T* begin;
	T* end;
	T* current;
public:
	friend void swap(vec &l, vec &r) {
		swap(l.begin, r.begin);
		swap(l.end, r.end);
		swap(l.current, r.current);
	}
	void allocate(unsigned sz) {
		begin = ...;
		end = ...;
		current = ...;
	}
	~vec() {...}
	explicit vec(unsigned c) {
		allocate(c);
	}
	vec(const vec &other) {
		allocate(other.end - other.begin);
		std::copy(other.begin, other.current, begin);
	}
	vec &operator=(vec other) {
		swap(*this, other);
		return *this;
	}
	vec(vec &&other) {
		swap(*this, other);
	}
	vec& operator=(vec&& other) {
		swap(*this, other);
		return *this;
	}
};

В общем написал какое-то Г, а теперь удивляешься, что не работает. Вообще в реальности 99% времени уходит на продумывание архитектуры/интерфейса/логические ошибки, а не на переписывание stl, я вот никогда свой вектор не писал.

kvpfs ★★
()
Ответ на: комментарий от technic93

Очнись! в расте с момента 1.0 добавили дофига всего очень важного, даже не говоря об асинках.

Да кстати по тем же массивам в последнем выпуске сняли ограничения по перечислению, до этого дабавили в дженерики числовые типы.

А если бы в расте были нормальные конст-дженерики то и дополнительные проверки можно бы было сделать.

Ну их тоже постепенно улучшают и наверно через несколько лет приблизятся к уровню С++ и D.

anonymous
()
Ответ на: комментарий от kvpfs

Это пять.

Ахахах, ты теперь меня косплеить начал )

А чего не спрятал внутри деление на ноль?

Зачем? Делить на ноль запрещено стандартом, а оставить объект в неопределённом состоянии с возможностью вызова деструктора - нет.

Прикинь как тут можно плюсовиков в дерьмо тыкнуть.

Ну ты не плюсовик, я уже говорил об этом. Кроме того, таким никаких плюсовиков ты никуда не ткнёшь - они об особенностях языка знают.

Я смотрю ты хорошо знаешь, за такой говнокод нужно руки выдрать, посмотри сколько тут дубляжа …

У тебя слишком примитивные попытки демагогии. Вот сейчас ты попытался съехать с темы, но снова неудачно.

В общем написал какое-то Г, а теперь удивляешься, что не работает.

Да, похоже ты снова ничего не понял. Подскажу тебе - оно работает. Правда без твоих фантазий на тему возможных действий с объектом после мува. Убираешь push_back на мувнутом объекте - и вуаля.

Вообще в реальности 99% времени уходит на продумывание архитектуры/интерфейса/логические ошибки, а не на переписывание stl, я вот никогда свой вектор не писал.

Не пытайся обманывать, у тебя не получается. Это я про 99% - ты про такие вещи ещё не знаешь. А про вектор, да - это я знаю.

anonymous
()
Ответ на: комментарий от anonymous

У тебя слишком примитивные попытки демагогии. Вот сейчас ты попытался съехать с темы, но снова неудачно.

Съехать? Не смеши меня, глядя на твое рукожопную портянку ясно, что ты примитивный хелоуворлдщик, и о плюсах рассуждать ты не в состоянии.

Да, похоже ты снова ничего не понял. Подскажу тебе - оно работает. Правда без твоих фантазий на тему возможных действий с объектом после мува. Убираешь push_back на мувнутом объекте - и вуаля.

Алё, это твой объект, делай и отвечай за него сам, пусть хоть исключение кидает, это твоё дело. STL же свои контейнеры делает юзабильными после мува или доказывай обратное.

kvpfs ★★
()
Ответ на: комментарий от kvpfs

Съехать? Не смеши меня, глядя на твое рукожопную портянку ясно, что ты примитивный хелоуворлдщик, и о плюсах рассуждать ты не в состоянии.

примитивный

Опять косплей ) Прекрати уже, говори своими словами )

Алё, это твой объект, делай и отвечай за него сам, пусть хоть исключение кидает, это твоё дело.

Зачем? Мне это не нужно, язык такого не запрещает. Я написал там выше, такое можно делать только с целью подстраховать низкоквалифицированных кодеров. Ну и чтобы теория use-after-move можно делать не рассыпалась. Но мне это не нужно.

STL же свои контейнеры делает юзабильными после мува или доказывай обратное.

Как же отчаянно ты пытаешься сохранить лицо ) Речь не про STL, а про язык, то есть C++ core. Про инварианты конкретных типов я уже говорил.

anonymous
()
Ответ на: комментарий от anonymous

Зачем? Мне это не нужно, язык такого не запрещает. Я написал там выше, такое можно делать только с целью подстраховать низкоквалифицированных кодеров. Ну и чтобы теория use-after-move можно делать не рассыпалась. Но мне это не нужно.

Ну и на здоровье пиши свой пет проектик как хочешь. А вот если опубликуешь и я заюзаю, то увидев падение после use after move - твоя поделка пойдёт в мусорное ведро, ибо язык также не запрещает такое использование.

Пора заканчивать.

kvpfs ★★
()
Ответ на: комментарий от kvpfs

А вот если опубликуешь и я заюзаю

Я хотел бы на это посмотреть, наверняка было бы весело ) Такой разрыв шаблона был бы )

то увидев падение после use after move - твоя поделка пойдёт в мусорное ведро, ибо язык также не запрещает такое использование.

Школота, школота… Язык описывает использование своих сущностей, а не сущностей внешнего мира.

Ладно, с возрастом пройдёт, наверное.

anonymous
()
Ответ на: комментарий от anonymous

А чего ты упёрся? Тебе сложно сделать нормально? Это ничего не стоит (если объекту вообще нужен move, конечно). Ну на крайняк запрети вовсе move раз не умеешь, сделай пометку в коде:

// Sory guys, but i am bungler, object does not support move operations.
class Shit {
};

Может сжалятся над криворуким.

kvpfs ★★
()
Ответ на: комментарий от fsb4000

Ну так да, но причина не ясна. Когда вектор не умеет перемещаться - это странно.

kvpfs ★★
()
Ответ на: комментарий от anonymous

Лучше всего прочитать доку по классу и узнать что происходит при муве.

technic93
()
Ответ на: комментарий от kvpfs

А чего ты упёрся? Тебе сложно сделать нормально?

Я же говорю - ты не знаешь, о чём пытаешься рассуждать. Вот и доказательства:

Это ничего не стоит (если объекту вообще нужен move, конечно).

Ну на крайняк запрети вовсе move раз не умеешь, сделай пометку в коде:

object does not support move operations.

Это при том, что move там поддерживается. Ты выучил бы уже плюсцы, а то который пост уже не можешь понять, что мув там рабочий, нерабочие там фантазии use-after-move можно спокойно делать. Я уже говорил - мне не нужно подстраховывать некомпетентных кодеров.

anonymous
()
Ответ на: комментарий от anonymous

Я прекрасно понял от чего твое поделие не работает, повторяю ещё раз - код дерьмо, его автор рукожоп. По тебе вижу, что язык знаю в разы лучше тебя и меня бесит, когда такие неучи х*ями кроют его являясь некомпетентными. Всю, с тобой закончил.

kvpfs ★★
()
Ответ на: комментарий от anonymous

use-after-move можно спокойно делать.

что значит спокойно? Если у тебя вектор пустой после мува, то ты не можешь обратится к элементу номер три, прикинь? А ещё без всяких мувов нельзя обратится к элементу пять если в векторе их всего три. Какие-то анонимусы вообще слабенькие пошли.

technic93
()
Ответ на: комментарий от kvpfs

Я прекрасно понял от чего твое поделие не работает, повторяю ещё раз - код дерьмо, его автор рукожоп.

Интересная штука - отрицание реальности ) Ты сам себе здесь противоречишь - либо не понял, либо код таки не дерьмо.

По тебе вижу, что язык знаю в разы лучше тебя и меня бесит, когда такие неучи х*ями кроют его являясь некомпетентными. Всю, с тобой закончил.

Школота подорвалась. Ну да, а что ещё делать когда всё против тебя. Не признавать же, что был не прав.

Но давай всё таки разберёмся. Вот ты утверждаешь, что мув нерабочий. Код там простой, значит можно продемонстрировать неработоспособность. Условие всего одно - показать что после выполнения vec v2 = static_cast<vec<int>&&>(v1); из примера v2 находится в невалидном состоянии или v1 не может быть корректно уничтожен вызовом деструктора.

Если это не так, то мув корректен, потому как больше никаких требований к нему нет.

anonymous
()
Ответ на: комментарий от technic93

Если у тебя вектор пустой после мува, то ты не можешь обратится к элементу номер три, прикинь?

Это была цитата, прикинь?

А ещё без всяких мувов нельзя обратится к элементу пять если в векторе их всего три.

Ага.

Какие-то анонимусы вообще слабенькие пошли.

Ахахах, и не говори ) Только регистранты, а не анонимы.

anonymous
()
Ответ на: комментарий от anonymous

Кстати.

Компилятор нас бережёт :)

Warning	C26800	Use of a moved from object: ''v1'' (lifetime.1)

https://imgur.com/a/qGu4Rdq

https://docs.microsoft.com/en-us/cpp/code-quality/c26800?view=msvc-160

fsb4000 ★★★★★
()
Последнее исправление: fsb4000 (всего исправлений: 1)
Ответ на: комментарий от anonymous

gcc -Wall -Wextra/clang -Weverything молча срабатывают.

clang-tidy это тоже находит. (правда пока это в альфа версии проверок clang-tidy)

https://imgur.com/a/2IXgVDI

https://clang.llvm.org/docs/analyzer/checkers.html#alpha-cplusplus-misusedmovedobject-c

gcc -fanalyzer тоже что-то страшное выдал :)

 In member function 'void vec<T>::push_back(const T&) [with T = int]':
<source>:36:17: warning: dereference of NULL '0' [CWE-476] [-Wanalyzer-null-dereference]
   36 |                 new(current) T{i};
      |                 ^~~~~~~~~~~~~~~~~

https://gcc.godbolt.org/z/Tr84E4hKP

fsb4000 ★★★★★
()
Последнее исправление: fsb4000 (всего исправлений: 1)
Ответ на: комментарий от fsb4000

dereference of NULL

Ну да, место и причина верно указана. И трейс есть. Классно. Правда у меня в 8 этого нет. 10+ как я понял.

anonymous
()
Ответ на: комментарий от fsb4000

clang-tidy это тоже находит

Именно поэтому в clang есть атрибут callable_when(unconsumed) чтобы отключить эту проверку для методов которые разрешается вызывать.

gcc что-то страшное выдал

gcc проанализировал весь граф вызовов (насколько смог) и нашёл косяк. В отличии от шланга, который просто запрещает вызов любого метода без нужного атрибута.

technic93
()
Ответ на: комментарий от anonymous

мув корректен, потому как больше никаких требований к нему нет.

этот тупой анонимус корректен, потому что больше никаких требований к нему нет.

technic93
()
Ответ на: комментарий от technic93

Ещё один порвался ) Ладно, не расстраивайся. Подрастёшь - тоже сможешь что-то дельное сказать(с большой вероятностью, как минимум).

anonymous
()
Ответ на: комментарий от anonymous

Зачем ты так быстро сливаешься?

Если до тебя не доходит что «требований к реализации со стороны стандарта нету» не противоречит «моя реализация может давать дополнительные гарантии», то перечитай всё ещё раз и подумай.

technic93
()
Ответ на: комментарий от anonymous

Нет. Там нечего воровать - это раз. А два оно работает совершенно по другому принципу во многих случаях.

В этом то и фишка, что в говнорасте ничего нет. Это всё примитивное дерьмо. Оно никому ненужно было, потому что не работает нихрена.

А происходит это по банальному принципу. Если завтра все начнут массово верить в том, что зелёные машины лучше любых других, то любой производитель будет их выпускать и выпускать больше остальных. Не потому что это действительно так, не потому что он в этом верит. Просто такова реальность.

anonymous
()
Ответ на: комментарий от technic93

Зачем ты так быстро сливаешься?

Зачем ты приписываешь мне какие-то голоса из своей головы?

Если до тебя не доходит что «требований к реализации со стороны стандарта нету» не противоречит «моя реализация может давать дополнительные гарантии», то перечитай всё ещё раз и подумай.

Школота, школота… Я тебе напомню, что обсуждались именно требования стандарта. Но поскольку у меня здесь аудитория, так сказать, нестандартная, то я и про конкретные типы также объяснил(на предмет могут давать). Перечитывай, зачем ты что-то пытаешься, если сам запутался?

anonymous
()
Ответ на: комментарий от anonymous

также объяснил

что ты там объяснил? ты родил такой говнокод (если это ты был а не другой анонимус), что мы ржали всем лором над ним.

technic93
()
Ответ на: комментарий от technic93

что ты там объяснил?

Ну ты чего, совсем что-ли тупой? Выше было, я даже процитирую:

Т. е. возможность дёргать [произвольные методы перемещённого объекта] должна быть явно обеспечена для конкретного типа. По умолчанию [согласно требованиям стандарта к произвольному типу] ничего там дёрнуть нельзя.

И вот обеспечение этой возможности для приведённого примера:

Ну и фикс здесь rhs.end = nullptr.

Море пафоса и ноль аргументации. Действительно что-ли про зумерков правду пишут )

ты родил такой говнокод (если это ты был а не другой анонимус), что мы ржали всем лором над ним.

Ну тебе просто ярость глаза застилает, от того что ты неправ здесь оказался. Иначе невозможно объяснить, что ты самостоятельно не смог понять пару строк. Убери максимализм, здесь он тебе только помешает.

anonymous
()
Ответ на: комментарий от anonymous

И что произойдёт с while (current != begin) в деструкторе если ты обнули rhs.begin но не обнулил rhs.current

А потом пишешь, «ну надо ещё current обнулить». А какое отношение это имеет к другим методам? У тебя там вообще кроме конструкторов и деструкторов ничего нету.

А понял, ты потом таки пофиксил и намекаешь на push_back. Правильно, не любой метод можно дёргать.

По умолчанию ничего там дёрнуть нельзя.

Я тебе и говорю, что это странная аргументация. По умолчанию много чего нельзя дёргать, безотносительно мува. Стандарт требует деструктор, потому что он будет его дёргать. А какой-то метод какого-то класса - ты сам решаешь можно его дергать или нет.

Типа обычно предполагается что нету смысла дергать что либо после мува, отсюда и соответствующие линты в clang/студии.

Там @kvpfs говорил что «можно дергать что угодно» он тоже не прав.

technic93
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.