13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607

Фабричный метод и RAII

15.12.2019, 23:14. Показов 2548. Ответов 13
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
У меня возник вопрос, как реализовать фабричный метод чтобы он соответствовал идиомы raii. Кто в данном случае является ответственным за создание обекта: сам метод или тот кто его взывает ?
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
15.12.2019, 23:14
Ответы с готовыми решениями:

Шаблон RAII замены указателя на функцию
шаблон raii замены указателя на фукнцию допустим имеется набор указателей на функции разных типов и существует потребность временно,...

RAII: внутри функции и можно ли в ней заменить new?
По наводке Убежденный стал разбираться с RAII, но по мере чтения инфы по сабжу возникают вопросы. Например, как создавать RAII для...

Фабричный метод: для чего он нужен?
Допустим есть такой код: #include <iostream> using std::cout; class Nature{ public: virtual void info() = 0; ...

13
495 / 209 / 70
Регистрация: 27.05.2016
Сообщений: 557
16.12.2019, 01:27
Фабричный метод берет на себя обязанности по созданию RAII обекта. Клиентский код им пользуеться и по выходу этого обекта из своего скоупа он уничтожаеться (освобождает выделенную под себя память, ресурсы и т. п.).
0
13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607
16.12.2019, 01:38  [ТС]
Цитата Сообщение от notAll Посмотреть сообщение
Фабричный метод берет на себя обязанности по созданию RAII обекта. Клиентский код им пользуеться и по выходу этого обекта из своего скоупа он уничтожаеться (освобождает выделенную под себя память, ресурсы и т. п.).
У фабричного метода несколько реализаций:
1)С помощью свитча
2)С помощью фабрик на основе синглтона Майерса
В певом случае мы должны создать в классе фабричного метода метод для освобожени ресурса и свой вариант умного указателя (scoped-ptr)
Во втором случае тоже самое. Это всё дикий оверхэд.
Самое разумное тогда делать гибрид фабричного метода и прототипа. Фабрика генерирует объекты и сохранет указатели на них в std::set
А в деструкторе фабрики мы проходя по std::set <Class*> удалим все объекты, но это не чистый фабричный метод.
0
 Аватар для zayats80888
6344 / 3515 / 1428
Регистрация: 07.02.2019
Сообщений: 8,980
16.12.2019, 01:39
Цитата Сообщение от squareroot Посмотреть сообщение
У меня возник вопрос, как реализовать фабричный метод чтобы он соответствовал идиомы raii
пусть возвращает smart pointer (создал и забыл)
1
495 / 209 / 70
Регистрация: 27.05.2016
Сообщений: 557
16.12.2019, 01:46
Цитата Сообщение от squareroot Посмотреть сообщение
мы должны создать в классе фабричного метода метод для освобожени ресурса и свой вариант умного указателя
Не должна фабрика освобождать ресурсы сконструированых обектов. Она должна конструировать RAII обекты (те же смарт поинтеры) и забывать про них раз и навсегда.
0
13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607
16.12.2019, 01:51  [ТС]
Цитата Сообщение от notAll Посмотреть сообщение
Не должна фабрика освобождать ресурсы сконструированых обектов. Она должна конструировать RAII обекты (те же смарт поинтеры) и забывать про них раз и навсегда.
Да, понял. Теперь всё ок. Правда есть ложка дёгтя. для unique_ptr надо будет явно прописывать std::move, а shared_ptr часто избыточен.
0
495 / 209 / 70
Регистрация: 27.05.2016
Сообщений: 557
16.12.2019, 01:59
Цитата Сообщение от squareroot Посмотреть сообщение
для unique_ptr надо будет явно прописывать std::move
Зачем, есть же правила RVO и NRVO. А в клиентском коде можно unique_ptr, возвращенный фабрикой, зразу же присваивать shared_ptr, если нужно его совместное использование.
0
13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607
16.12.2019, 02:07  [ТС]
Цитата Сообщение от notAll Посмотреть сообщение
Зачем, есть же правила RVO и NRVO. А в клиентском коде можно unique_ptr, возвращенный фабрикой, зразу же присваивать shared_ptr, если нужно его совместное использование.
Если я ничего не путаю, то RVO/NRVO относиться к копированию, а не к перемещению, но shared_ptr оставляю за скобками. При использовании семантики перемещения в возвращаемом из фабричного метода параметре без std::move появится dangled reference и как следствие UB.
А с std::move немного теряется идея фабричного метода (абстракция от процесса создания)
0
495 / 209 / 70
Регистрация: 27.05.2016
Сообщений: 557
16.12.2019, 02:17
Цитата Сообщение от squareroot Посмотреть сообщение
При использовании семантики перемещения в возвращаемом из фабричного метода параметре без std::move появится dangled reference и как следствие UB
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#include <memory>
 
struct Factory
{
    std::unique_ptr<int> make() const
    {
        return std::make_unique<int>(42);
    }
};
 
int main()
{
    Factory factory;
    std::shared_ptr<int> sharedObj = factory.make();
    std::unique_ptr<int> uniqueObj = factory.make();
}
Где здесь dangled reference и UB?
0
13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607
16.12.2019, 02:20  [ТС]
Цитата Сообщение от notAll Посмотреть сообщение
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#include <memory>
 
struct Factory
{
    std::unique_ptr<int> make() const
    {
        return std::make_unique<int>(42);
    }
};
 
int main()
{
    Factory factory;
    std::shared_ptr<int> sharedObj = factory.make();
    std::unique_ptr<int> uniqueObj = factory.make();
}
Где здесь dangled reference и UB?
У unique_ptr закрытый конструктор копирования, а вы возращаете его по значению. Я чегото не понимаю похоже. Я наверно чегото не знаю, но на мой делетантский взгляд такой код не скомпилируется.
0
495 / 209 / 70
Регистрация: 27.05.2016
Сообщений: 557
16.12.2019, 02:28
Цитата Сообщение от squareroot Посмотреть сообщение
У unique_ptr закрытый конструктор копирования, а вы возращаете его по значению
В даном случае сработает опртимизация компилятора RVO. Рекомендую почитать, что это такое. Еще в новой книге Меерса есть целая глава про RVO/NRVO и std::move.
1
13 / 13 / 1
Регистрация: 19.10.2019
Сообщений: 607
16.12.2019, 04:31  [ТС]
Цитата Сообщение от notAll Посмотреть сообщение
В даном случае сработает опртимизация компилятора RVO. Рекомендую почитать, что это такое. Еще в новой книге Меерса есть целая глава про RVO/NRVO и std::move.
Я знаю что это такое. Сработает она или не сработает зависит от флагов компиляции.

Добавлено через 3 минуты
Странно, но QMAKE_CXXFLAGS += -fno-elide-constructors не останавливает.

Добавлено через 45 минут
Цитата Сообщение от notAll Посмотреть сообщение
В даном случае сработает опртимизация компилятора RVO. Рекомендую почитать, что это такое. Еще в новой книге Меерса есть целая глава про RVO/NRVO и std::move.
Спасибо, но можно ссылку ?
Мне казалось я знаю всё, но вы меня разубедили и щас голова пухнет от того как всё нетривиально.
Пока нарыл https://en.cppreference.com/w/... py_elision и мне тяжело соорентироваться где мой случай.
Тут ещё работает какойто механизм автовыбора между копированием и перемещением.
Буду благодарен если объясните на пальцах.

Добавлено через 1 час 11 минут
Всё, спасибо, нашёл книгу.
0
19458 / 10070 / 2452
Регистрация: 30.01.2014
Сообщений: 17,751
16.12.2019, 09:14
Цитата Сообщение от squareroot Посмотреть сообщение
Мне казалось я знаю всё
Опасно так думать, даже после двух десятков (или больше) лет опыта.

Цитата Сообщение от squareroot Посмотреть сообщение
А с std::move немного теряется идея фабричного метода (абстракция от процесса создания)
Я бы так не сказал.
Представьте, что вы строите дом.
Вы можете его построить с использованием гвоздей или шурупов и досок, скоб, срубить его топором из бревен, выложить из кирпича и т.д. По разному построенный дом - это все равно дом. Идея дома не теряется от того, как именно вы его строите. Идея дома - это абстракция гораздо более высокого порядка, чем гвозди. В данном случае std::move - это всего лишь гвоздь, или что-то около того.
0
Эксперт С++
 Аватар для hoggy
8973 / 4319 / 960
Регистрация: 15.11.2014
Сообщений: 9,760
16.12.2019, 13:41
Цитата Сообщение от squareroot Посмотреть сообщение
Сработает она или не сработает зависит от флагов компиляции.
не зависит.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
16.12.2019, 13:41
Помогаю со студенческими работами здесь

DLL, RAII для интерфеса
Речь пойдёт, само собой, о неявно подключаемой dll для хранения классов. Решил пойти в сторону интерфейсов и фабрик классов, тут вроде всё...

Фабричный метод
Добрый вечер. Заранее извиняюсь за создание темы о паттерне в этом разделе (в соответствующем разделе видел похожие темы но для php, в...

Паттерн фабричный метод
Нужно в C# привести пример работы паттерна фабричный метод. Выручайте, желательно готовый код, чтобы копипастом работало все. Нету...

Фабричный метод и паттерн фабрика
подскажите в чем разница увидел пример фабричного метода не понял его public MyClass Factory(int i, int j) { MyClass t =...

Как работать с коллекцией через Фабричный метод
Всем привет, я попробовал реализовать Фабричный метод Вот что получилось Класс продукт, там 1 абстрактный класс и 2 конкретных ...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
14
Ответ Создать тему
Опции темы

Новые блоги и статьи
Реализация многопоточных сетевых серверов на Python
py-thonny 16.05.2025
Когда сталкиваешься с необходимостью писать высоконагруженные сетевые сервисы, выбор технологии имеет критическое значение. Python, со своей элегантностью и высоким уровнем абстракции, может. . .
C# и IoT: разработка Edge приложений с .NET и Azure IoT
UnmanagedCoder 16.05.2025
Мир меняется прямо на наших глазах, и интернет вещей (IoT) — один из главных катализаторов этих перемен. Если всего десять лет назад концепция "умных" устройств вызывала скептические улыбки, то. . .
Гибридные квантово-классические вычисления: Примеры оптимизации
EggHead 16.05.2025
Гибридные квантово-классические вычисления — это настоящий прорыв в подходах к решению сложнейших вычислительных задач. Представьте себе союз двух разных миров: классические компьютеры, с их. . .
Использование вебсокетов в приложениях Java с Netty
Javaican 16.05.2025
HTTP, краеугольный камень интернета, изначально был спроектирован для передачи гипертекста с минимальной интерактивностью. Его главный недостаток в контексте современных приложений — это. . .
Реализация операторов Kubernetes
Mr. Docker 16.05.2025
Концепция операторов Kubernetes зародилась в недрах компании CoreOS (позже купленной Red Hat), когда команда инженеров искала способ автоматизировать управление распределёнными базами данных в. . .
Отражение в C# и динамическое управление типами
stackOverflow 16.05.2025
Reflection API в . NET — это набор классов и интерфейсов в пространстве имён System. Reflection, который позволяет исследовать и манипулировать типами, методами, свойствами и другими элементами. . .
Настройка гиперпараметров с помощью Grid Search и Random Search в Python
AI_Generated 15.05.2025
В машинном обучении существует фундаментальное разделение между параметрами и гиперпараметрами моделей. Если параметры – это те величины, которые алгоритм "изучает" непосредственно из данных (веса. . .
Сериализация и десериализация данных на Python
py-thonny 15.05.2025
Сериализация — это своего рода "замораживание" объектов. Вы берёте живой, динамический объект из памяти и превращаете его в статичную строку или поток байтов. А десериализация выполняет обратный. . .
Чем асинхронная логика (схемотехника) лучше тактируемой, как я думаю, что помимо энергоэффективности - ещё и безопасность.
Hrethgir 14.05.2025
Помимо огромного плюса в энергоэффективности, асинхронная логика - тотальный контроль над каждым совершённым тактом, а значит - безусловная безопасность, где безконтрольно не совершится ни одного. . .
Многопоточные приложения на C++
bytestream 14.05.2025
C++ всегда был языком, тесно работающим с железом, и потому особеннно эффективным для многопоточного программирования. Стандарт C++11 произвёл революцию, добавив в язык нативную поддержку потоков,. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru