Модераторы: Daevaorn

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Указатель на функцию-член, Использование сабжа для классов-потомков 
:(
    Опции темы
ZeusAtVingrad
Дата 22.11.2013, 20:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 82
Регистрация: 12.4.2006

Репутация: нет
Всего: нет



Я так понимаю, что std::bind появилась в C++11?
А ранее его надо было искать в boost?
PM MAIL   Вверх
xvr
Дата 22.11.2013, 22:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 60
Всего: 223



Цитата(ZeusAtVingrad @  22.11.2013,  20:09 Найти цитируемый пост)
Я так понимаю, что std::bind появилась в C++11?

Гораздо раньше. А вот std::function<> - в C++ 11

PM MAIL   Вверх
vinter
Дата 23.11.2013, 07:19 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Explorer
****


Профиль
Группа: Завсегдатай
Сообщений: 2735
Регистрация: 1.4.2006
Где: Н.Новгород

Репутация: 13
Всего: 56



в принципе да, в C++11(раньше он был в особом namespace std::tr1). Раньше был std::bind1st и std::bind2nd. Их, кстати, в твоём случае тоже хватит. 



--------------------
Мой блог
PM MAIL WWW   Вверх
ZeusAtVingrad
Дата 25.11.2013, 23:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 82
Регистрация: 12.4.2006

Репутация: нет
Всего: нет



Другая проблема встала Тестовый пример.

Два класса (B и C) наследника от одного (А).
У наследников, у обоих есть функции получения значения int.
Они могут вернуть std::function<void(int)> - чтобы можно было вызвать эти функции.
Кому надо - могут сохранить, чтобы вызвать потом (т.о. установить "связь" (link) для рассылки значений).

Вопрос:
можно ли из базового класса (A) как-то убрать упоминание int?
Потому что сигнатуры функций у классов-наследников могут быть разными и базовому классу они неизвестны.

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

Мне пока видится: заворачивать возвращаемую std::function<void(int)> во что-то вроде boost::any а вызывающий пусть сравнивает - совпадает ли тип с тем, что он ожидал или нет.

Ещё вариант - гонять собственно сами значения через boost::any. Тогда и шаблон в базовом классе будет выглядеть как
std::function<void(const boost::any&)> - и не важно какие именно типы нужны классам-наследникам.
Этот путь не очень красивый архитектурно получается (в наследниках, при программировании уже собственно компонентов) и медленнее, чем гонять значения непосредственно в их собственных типах.


Или может паттерн проектирования какой-то подходящий есть и я просто туплю?


И второй вопрос - касаемо этих самых std::bind'ов и std::function.
В стандартной библиотеке предусмотрен механизм защиты от удаления объекта - того, на который мы имеем std::function? Чтобы программа не падала, а исключение например выбрасывала, что, мол, объекта уже нет. Или что-то вроде этого.
Или придётся самому колхозить?


Это сообщение отредактировал(а) ZeusAtVingrad - 25.11.2013, 23:20
PM MAIL   Вверх
xvr
Дата 26.11.2013, 08:52 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 60
Всего: 223



Цитата(ZeusAtVingrad @  25.11.2013,  23:05 Найти цитируемый пост)
Между собой классы-наследники уж как-нибудь договорятся

Для того, что бы они договорились у них обоих должна присутствовать сигнатура на этапе компиляции. Тогда можно получение этой function завернуть в другой класс, у которого будет явно присутствовать тип в сигнатуре метода получения function. Все такие классы должны быть наследником одного базового (назовем его GenericSource, у него вообще не будет метода для получения function), и именно его должен возвращать A. Все конкретные сигнатуры должны быть как то перечислены (либо строкой, либо GUID'ом, либо можно попробовать явно вывести некую константу из типа), и в классе A должен быть метод для получения GenericSource по сигнатуре. 
Код

// Generic callback
struct GenericSource {
 virtual ~GenericSource() {}
};

// Convert type -> unique const
template<class Source>
class SourceTrait {
 static void stub() {}
public:
 const size_t Trait = (size_t)&stub;
};

// Concrete callback - void (int)
struct SourceInt : public GenericSource {
 virtual std::function<void(int)> get(const char* name) =0;

 const size_t Trait = SourceTrait<void(int)>::Trait;
};


// Source of callbacks - inherit this class if you want to be source of callback functions
struct Sink {
 virtual GenericSource* get_callback_by_type(size_t type_trait) = 0;
};

/////// Usage
class MyClass : public Sink {
  ...
 virtual GenericSource* get_callback_by_type(size_t type_trait)
  {
    if (type_trait == SourceInt::Trait) return &my_source_int; // my_source_int - field in class MyClass of type derived from SourceInt
    ...
  }
};

// call site
GenericSource* src = obj->get_callback_by_type(SourceInt::Trait);
SourceInt* real_src = (SourceInt*)src;
... real_src->get("first_callback"); ...



Цитата(ZeusAtVingrad @  25.11.2013,  23:05 Найти цитируемый пост)
В стандартной библиотеке предусмотрен механизм защиты от удаления объекта - того, на который мы имеем std::function? 

Нет

Цитата(ZeusAtVingrad @  25.11.2013,  23:05 Найти цитируемый пост)
Или придётся самому колхозить?

Придется. Например введением общего менеджера на все объекты, который будет содержать общее оглавление всех объектов в системе (ведь как то они должны друг друга находить). Заодно он может и выступать в качестве посредника при вызове callback'ов. Так как он сам никуда не денется, то такие вызовы будут безопасны (конечно он сам должен отслеживать разпушение объектов-приемников и не пытаться передать вызов им)


PM MAIL   Вверх
ZeusAtVingrad
Дата 26.11.2013, 22:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 82
Регистрация: 12.4.2006

Репутация: нет
Всего: нет



Честно говоря - я ничего в коде не понял.
Зачем шаблон, параметр которого не используется?
Зачем в нём константа Trait которая равна адресу статической функции приведённой к... size_t?
PM MAIL   Вверх
xvr
Дата 27.11.2013, 09:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 60
Всего: 223



Цитата(ZeusAtVingrad @  26.11.2013,  22:05 Найти цитируемый пост)
Зачем в нём константа Trait которая равна адресу статической функции приведённой к... size_t? 

Для каждого типа шаблона будет сгенерена своя статическая функция (по 1 штуке на каждый тип). Ее адрес будет уникальный. Таким образом для каждого типа шаблона (сигнатуры вашего callback'а) получим уникальное число.

PM MAIL   Вверх
ZeusAtVingrad
Дата 27.11.2013, 09:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 82
Регистрация: 12.4.2006

Репутация: нет
Всего: нет



Мда. Интересный подход.

А зачем приводить к site_t?
И ещё - этот способ быстрее, чем std::type_info?
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0820 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.