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

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> контейнер, функтор и шаблоны 
:(
    Опции темы
zss
Дата 3.3.2006, 09:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



подскажите пожалуйста можно ли так сделать

есть функтор
Код

template <class T>
struct Destroyer {
    void operator () (T*& object) const {
        if (!object) return;
        delete object;
        object = NULL;
    }
};


он используется для удаления объектов, указатели которых
храняться в контейнере (любом)

хочется для контейнера создать функцию, которая убивала бы
объекты по необходимости (в зависимости от функтора)

что-то вроде
Код

template <typename T, class Container = std::vector<T> >
void DestroyContainer<T, Container > (Container<T>& container) {

    std::for_each (container.begin(), container.end(), Destroyer <T> ());
    connections_.erase (
        std::remove (container.begin(), container.end(), (T *)NULL),
        container.end()
    );
}



только хотелось бы еще и сам функтор задавать шаблонами
Тоесть чтоб функция работала для любого контейнера с заданным функтором
PM MAIL ICQ   Вверх
Daevaorn
Дата 3.3.2006, 10:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2155
Регистрация: 29.11.2004
Где: Москва

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



zss,
Если в первом коде вроде всё нормально, то во втором куча проблем.

1. template <typename T, class Container = std::vector<T> > - спрашивается зачем дефолтить шаблонный параметр, да ещё и вектором. Не надо!

2. void DestroyContainer<T, Container > (Container<T>& container) { - зачем после имени функции опять перечислять шаблонные параметры? Не надо, шаблонные функции всё равно нельзя специализировать!

3. template <typename T, class Container, class Func > - тогда в коде пишешь std::for_each (container.begin(), container.end(), Func() ); и получаешь совсем обощённый механизм. Но тогда меняй название.

4. connections_.erase (
std::remove (container.begin(), container.end(), (T *)NULL),
container.end()
);

ну вот тут тоже не всё понятно, чего ты хочешь если у тебя функтор удаляет все элементы. Может просто clear() вызвать?

PM MAIL WWW   Вверх
zss
Дата 3.3.2006, 10:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата(Daevaorn @ 3.3.2006, 10:35 Найти цитируемый пост)
спрашивается зачем дефолтить шаблонный параметр, да ещё и вектором. Не надо!

а чем это плохо ?

Цитата(Daevaorn @ 3.3.2006, 10:35 Найти цитируемый пост)
Не надо, шаблонные функции всё равно нельзя специализировать!

если не ошибаюсь - нельзя частично специализировать

Цитата(Daevaorn @ 3.3.2006, 10:35 Найти цитируемый пост)
ну вот тут тоже не всё понятно, чего ты хочешь если у тебя функтор удаляет все элементы. Может просто clear() вызвать?

это этот функтор все удаляет.
А если я подсуну функтор, который будет дергать методы класса и
в зависимости от результата решать - удалять или нет

для этого я и хочу функтор задавать шаблонно
PM MAIL ICQ   Вверх
Daevaorn
Дата 3.3.2006, 10:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2155
Регистрация: 29.11.2004
Где: Москва

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



Цитата(zss @ 3.3.2006, 11:41 Найти цитируемый пост)
а чем это плохо ?

А чем это хорошо? Что тебе это дает? Боюсь, что совсем ничего.

Цитата(zss @ 3.3.2006, 11:41 Найти цитируемый пост)
если не ошибаюсь - нельзя частично специализировать

Да. Но это не меняет сути, зачем потом писать параметры опять?

Цитата(zss @ 3.3.2006, 11:41 Найти цитируемый пост)
это этот функтор все удаляет.
А если я подсуну функтор, который будет дергать методы класса и
в зависимости от результата решать - удалять или нет

Я именно твоего данный код имел ввиду.
PM MAIL WWW   Вверх
zss
Дата 3.3.2006, 11:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата(Daevaorn @ 3.3.2006, 10:52 Найти цитируемый пост)
А чем это хорошо? Что тебе это дает? Боюсь, что совсем ничего.

меньше писать smile


Цитата(Daevaorn @ 3.3.2006, 10:52 Найти цитируемый пост)
Да. Но это не меняет сути, зачем потом писать параметры опять?

согласен - аналогично моему ответу выше smile

Daevaorn, только немного не понятно почему
Код

template <typename T, class Container, class Func >


не понятно, что Container и Func зависят от T

я думал что будет что-то вроде
Код

template <template <class T> class Container, class Func >


только Func опять не зависит от T
PM MAIL ICQ   Вверх
Daevaorn
Дата 3.3.2006, 11:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2155
Регистрация: 29.11.2004
Где: Москва

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



zss,
Если брать твой первоначальный код, то параметр T тебе был нужен лишь для того, тобы создать функтор. Но когда у тебя уже функтор как паремтр шаблона, то можно отказаться и от T. Он не нужен. Всё работу по этому поводу будет выполнять клиентский код, который в зависимости от ситуации будет сам выбирать парметры для функтора.
И ещё, допустим, у вектора и один шаблонный параметр (ну если уже совсем быть точным, то только обязательный один), но это не значит, что у всех других контейнеров тоже самое. Так, что твой вариант ещё теряет обобщенность smile
PM MAIL WWW   Вверх
zss
Дата 3.3.2006, 13:08 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Daevaorn, довольно убедительно - принимается

только хотелось бы для общего развития (и так сказать для закрепления)
увидеть еще варианты (желательно с параметрами по-умолчанию)
PM MAIL ICQ   Вверх
Chaos A.D.
Дата 3.3.2006, 15:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 172
Регистрация: 16.1.2005
Где: 09 RUS

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



Я бы сделал так:
Код

template <class Iterator, class Functor>
void ApplyAndRemove( Iterator begin, Iterator end, Functor func )
{
    std::for_each(begin, end, func);
    std::erase( std::remove( begin, end, NULL ), end );
}


Это, ИМХО, как-то больше в стиле STL - функция работает с последовательностью.
По-моему, так более гибко.

Это сообщение отредактировал(а) Chaos A.D. - 3.3.2006, 15:38
--------------------
Надо смеяться над тем, что тебя мучит, иначе не сохранишь равновесия, иначе мир сведет тебя с ума...Ken Kesey - One Flew Over The Cocoo's Nest
PM MAIL   Вверх
zss
Дата 3.3.2006, 15:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Chaos A.D., а если итератор становится недействительным ?


P.S.
Daevaorn, твой код не хочет собираться
Код

template <typename T, class Container, class Functor >
void DestroyContainer (Container& container) {

    std::for_each (container.begin(), container.end(), Functor <T> ());
    connections_.erase (
        std::remove (container.begin(), container.end(), (T *)NULL),
        container.end()
    );
}

//тогда

std::vector<MyClass> myClass;
DectroyContainer <MyClass, std::vector<MyClass *>, Destroyer> (myClass);

PM MAIL ICQ   Вверх
Chaos A.D.
Дата 3.3.2006, 16:08 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 172
Регистрация: 16.1.2005
Где: 09 RUS

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



Я прогнал, erase это же функция-член контейнера...
--------------------
Надо смеяться над тем, что тебя мучит, иначе не сохранишь равновесия, иначе мир сведет тебя с ума...Ken Kesey - One Flew Over The Cocoo's Nest
PM MAIL   Вверх
Daevaorn
Дата 3.3.2006, 16:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2155
Регистрация: 29.11.2004
Где: Москва

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



zss,
Было бы странно, если это у тебя бы скомпилировалось.

Вот, как вариант:
Код

template <class T>
struct Destroyer
{
    void operator ()( T*& object )const
    {
        if (!object) return;
        delete object;
        object = NULL;
    }
};


template < class Container, class Functor >
void DestroyContainer(Container& container ) 
{
    std::for_each( container.begin(), container.end(), Functor() );
    container.erase (
        std::remove (container.begin(), container.end(), (Container::value_type)0 ),
        container.end()
    );
}


typedef std::vector<MyClass*> MyVector;
MyVectormyClass;

DestroyContainer< MyVector, Destroyer<MyClass> >( myClass );

PM MAIL WWW   Вверх
zss
Дата 3.3.2006, 17:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Daevaorn, а что я сейчас не так делаю

Код

template <class T>
struct Destroyer : public std::unary_function <T, bool> {

    bool operator () (T*& object) const {
        if (!T->SomeMethod()) return false;
        delete object;
        object = NULL;
        return true;
    }
};

template <class Container, class Functor>
void DestroyContainer (Container& container){

    container.erase (
            std::remove_if (container.begin(), container.end(),    Functor()),
            container.end()
    );
}

template <class T>
class SomeClass{
private :
    typedef std::vector<T*> MyVector;
    MyVector myClass;
public:
    virtual ~SomeClass (){
        DestroyContainer< MyVector, Destroyer<T> >( myClass );    
    }

}


ругается на строку
Код

if (!T->SomeMethod()) return false;


Почему ?
PM MAIL ICQ   Вверх
Daevaorn
Дата 3.3.2006, 17:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2155
Регистрация: 29.11.2004
Где: Москва

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



zss, Ты это серьезно?smile

if (!T->SomeMethod()) return false;

Т это у тебя что? Правильно, тип. Тогда как ты у типа можешь вызвать не статический метод, да ещё и оператором ->? Никак. Значит пиши object вместо T smile

Это сообщение отредактировал(а) Daevaorn - 3.3.2006, 17:50
PM MAIL WWW   Вверх
zss
Дата 3.3.2006, 17:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


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

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



Цитата(Daevaorn @ 3.3.2006, 17:49 Найти цитируемый пост)
Т это у тебя что? Правильно, тип. Тогда как ты у типа можешь вызвать не статический метод, да ещё и оператором ->? Никак. Значит пиши object вместо T

блин - все, приехали smile (суши весла smilesmilesmile)


Daevaorn, большое тебе человеческое ...

Это сообщение отредактировал(а) zss - 3.3.2006, 18:00
PM MAIL ICQ   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

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

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

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

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


 




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


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

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