
Vyacheslav
25.10.2018
12:16:18

Constantine
25.10.2018
12:16:29

Vyacheslav
25.10.2018
12:16:41
Так однозначнее

Google

Vyacheslav
25.10.2018
12:17:23

Matwey
25.10.2018
12:22:23
Смотрите какие я нашел стикеры

Ignat
25.10.2018
12:22:37
мм, свежачок

Igor
25.10.2018
12:24:14
с душой так, по-лебедевски

Constantine
25.10.2018
12:26:54
Давайте код целиком
примерно так
//у нас есть апиха для работы с guard_ptr
//guard_ptr make_guard(noexcept lambda)
//есть вспомогательный тип ref_with_guard
//по сути pair<A&, guard_ptr> только в одном указателе
//неперемещаемый с одним слотом для простоты
struct B {
ref_with_guard<A> a_ref(guard_ptr a_guard) & {
a_guard_ = std::move(a_guard);
return { a, [this] () { a_guard_ = nullptr; } };
}
private:
A a;
guard_ptr a_guard_;
};
//пользователь В, неперемещаемый
struct BUser {
ref_with_guard<A> a;
void init_with_b(B& b) {
a = b.a_ref(make_guard([this] () { a = nullptr; }));
}
};

Vyacheslav
25.10.2018
12:28:49
В pair нельзя положить unique_ptr без явного перемещения. Его я в коде не вижу

Constantine
25.10.2018
12:30:21

Vyacheslav
25.10.2018
12:30:53

Constantine
25.10.2018
12:31:05
Только через move.
std::unique_ptr<int> f() { return std::make_unique<int>(0); }
void g(std::unique_ptr<int>) {}
void foo() { g(f()); } //ok

Vyacheslav
25.10.2018
12:35:44
Ок, был не точен здесь

Google

Constantine
25.10.2018
12:36:45
Так как же эту конструкцию использовать?
А тут все работает - класс BUser просто оповестят если В сдох. Что там делать остается вопрос к нему.
Если вопрос debug проверок там становится чуть проще все это

Vyacheslav
25.10.2018
12:36:58
И что делает make_guard мне не понятно. Создаёт объект?

Constantine
25.10.2018
12:37:31

Vyacheslav
25.10.2018
12:40:29

Constantine
25.10.2018
12:40:51

Vyacheslav
25.10.2018
12:40:53
Возврат из a_ref поясните пожалуйста
Туда передается референс на а, так?

Constantine
25.10.2018
12:41:42
Возвращается пара из ссылки на А и действия по "мне больше не нужна ссылка"
Если предполагается debug проверка в конце типа "assert все хорошо" можно просто тот самый refcount на себя считать

Vyacheslav
25.10.2018
12:46:45
Я пока пытаюсь весь код понять. a = nullptr сбивает с толку в последнем методе. Я так понимаю, привэсваиыается пустой ref_with_guard, что в момент разрушения BUser не имеет большого смысла
Т.е. разделить доступ к А без проброски BUser во все использующие А методы не удастся.
Или же везде гонять ref_with_guard<A>, что мало чем отличается от, например, const shared_ptr<A>&
Жёсткое ограничение, что ссылкой на А владеет только один BUser, никуда не уходит.
То, что сброс в nullptr user2.a произойдёт раньше времени уничтожения B.a вопросов не вызывает.
Нюанс заключается в том, что в деструкторе A нет возможности обратиться к объемлющему классу B, т.к. он на тот момент уже разрушен. В моём примере такая возможность есть.


Nikita
25.10.2018
13:54:23
Всем ку
cppreference про std::array::front, в частности, говорит: Calling front on an empty container is undefined. Допускается ли реализация, которая вызывает ошибку компиляции?
или код должен компилиться

Евгений
25.10.2018
13:55:19

Nikita
25.10.2018
13:56:06

Евгений
25.10.2018
13:56:47
Sore, bur ju juzz said some DEACH.

Google

Евгений
25.10.2018
13:57:54

Alexander
25.10.2018
13:58:19

Xessao
25.10.2018
13:58:22
Всем привет, кто-нибудь пользуются PVS-Studio?

Alexander
25.10.2018
13:58:27

Nikita
25.10.2018
13:58:39

Alexander
25.10.2018
13:58:47

Xessao
25.10.2018
13:59:05
я
Можешь скинуть любой html отчёт? Нужно сделать одноразовый отчёт и хочу взять за базу их версию.

Alexander
25.10.2018
13:59:27

Nikita
25.10.2018
14:00:13
непонятно, как имплементить эти функции без массива) вроде как, нет легальных путей сделать ссылку на nullptr

Alexen
25.10.2018
14:01:36
У гцц посмотри
Там есть специализация для пустого

Nikita
25.10.2018
14:03:46
{ return *static_cast<_Tp*>(nullptr); } каеф блин

Andrey
25.10.2018
14:07:12

Nikita
25.10.2018
14:08:12

Ilia
25.10.2018
14:10:08

Nikita
25.10.2018
14:10:44

Andrey
25.10.2018
14:11:26

Google

Constantine
25.10.2018
14:12:05

Ilia
25.10.2018
14:12:18

Constantine
25.10.2018
14:12:54

Nikita
25.10.2018
14:13:24

Vyacheslav
25.10.2018
14:13:53

Nikita
25.10.2018
14:14:00
std::array<Foo, 3> myArr = { Foo(1), Foo(2), Foo(3) };

Vyacheslav
25.10.2018
14:16:03

Constantine
25.10.2018
14:16:15

Vyacheslav
25.10.2018
14:17:10

Andrey
25.10.2018
14:17:19

Nikita
25.10.2018
14:17:42

Constantine
25.10.2018
14:18:58
@webreh ^ вот здесь обратное поведение.
Это так не сработает. Вы не можете обращаться полноценно к В из деструктора А в вашем примере. Попытка использовать любой метод, требующий А, в деструкторе класса А приведет к UB (бесконечный цикл без side effect), которое будет зависанием из-за того, что компилятор не оптимизирует через аллокацию памяти

Vyacheslav
25.10.2018
14:19:25

Constantine
25.10.2018
14:21:11

Vyacheslav
25.10.2018
14:21:54

Constantine
25.10.2018
14:22:31

Vyacheslav
25.10.2018
14:24:22

Google

Александр
25.10.2018
14:25:50

Constantine
25.10.2018
14:28:56

Vyacheslav
25.10.2018
14:30:03
Имхо, в большом проекте я бы запутался.

Constantine
25.10.2018
14:30:25

Vyacheslav
25.10.2018
14:30:47

Constantine
25.10.2018
14:30:57

Vyacheslav
25.10.2018
14:32:16
Мне дубли такого рода сложно воспринимать. Уже привык, что 1 нетривиальная переменная = 1 сущность.

Constantine
25.10.2018
14:32:57

Vyacheslav
25.10.2018
14:33:45
Я думаю, пора тему закрывать. И тот, и тот подход имеет право на жизнь. Ваш мне сложнее для запоминания.

Kitsu
25.10.2018
14:34:18
А есть какие-нибудь особенности с class template instantiation у boost::variant? Все вроде как работало, затем разнес в header/cpp-impl в виде extern template class/template class и компилятор (clang 8) стал ругаться на invalid operands to binary expression (const T, const T)

Vyacheslav
25.10.2018
14:34:41

Constantine
25.10.2018
14:34:45
В общем из языков, которые не имеют императивов времени жизни

Kitsu
25.10.2018
14:35:57

Vyacheslav
25.10.2018
14:36:07