Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Общие вопросы > поиск в list stl


Автор: Hvoin 7.6.2008, 03:57
есть класс

Код

class parent 
{
    string Name;
    int Power;
};

от него наследут
class  children:public perent  
{
    int Run;
};



есть список
list<parent*> fact;

как сделать поиск по Name, Power и Run в списке fact?


 ! 
chipset
Теги [code] рулят форева.


Автор: chipset 7.6.2008, 08:11
1. Простейший случай: find_if.
2. Сложнейший случай: boost::lambda.

Автор: d06osipov 7.6.2008, 08:43
Общий случай: for;
Быстрее, чем for всё равно не получится, это же список

Автор: Lazin 7.6.2008, 09:35
ну можно еще отмапить список если скорость поиска критична... 

Код

std::list<parent*> values;

std::map<std::string, std::list<parent*>::iterator> name_mapping;

...

for(std::list<parent*>::iterator i = values.begin(); i != values.end(); ++i)
{
   name_mapping[ (*i)->Name ] = i;
}

parent* find_by_name(std::string name)
{
  return *(name_mapping[name]);
}

Автор: Rififi 7.6.2008, 12:13
Цитата(Hvoin @  7.6.2008,  03:57 Найти цитируемый пост)
как сделать поиск по Name, Power и Run в списке fact?

поиск по Name, Power - см. выше
поиск по Run - никак.

Автор: Hvoin 7.6.2008, 18:08
а если так
Код

list<parent*> fact;
parent* p;
string ss="Petr Petrov";
int ii=2;
int rr=22;
p= new children(ss,ii,rr);
fact.push_back(p);

у меня много наследников и поиск предназачен для них

как с помощью find_if найти ss,ii,rr...Знаю что нужно перегрузить () только где, и как...какой 
параметр должен быть третим...или rr нельзя найти с помощью find_if?

Код

Find_if(fact.begin(),fact.end(),???)

Автор: Rififi 7.6.2008, 20:25
Цитата(Hvoin @  7.6.2008,  18:08 Найти цитируемый пост)
как с помощью find_if найти ss,ii,rr...Знаю что нужно перегрузить () только где, и как...какой 


велосипедный способ
Код
template <typename T, typename Class, T Class::*member_ptr>
struct field_selector : public std::unary_function<Class*, bool>
{
    typedef std::unary_function<Class*, bool> base_type;
    typedef typename base_type::argument_type argument_type;
    typedef typename base_type::result_type result_type;

    field_selector(const T& v) : v_(v) {}
    result_type operator()(const argument_type& it) const { return v_ == it->*member_ptr; }
    T v_;
};

std::vector<parent*> v;
std::find_if(v.begin(), v.end(), field_selector<int, parent, &parent::Power>(2));
std::find_if(v.begin(), v.end(), field_selector<std::string, parent, &parent::Name>("Petr Petrov"));


boost-способ
Код
std::vector<parent*> v;
std::find_if(v.begin(), v.end(), boost::bind(&parent::Power, _1) == 2);
std::find_if(v.begin(), v.end(), boost::bind(&parent::Name, _1) == "Petr Petrov");


Автор: Hvoin 7.6.2008, 21:06
спасибо

Автор: chipset 7.6.2008, 21:10
Метод Rififi не решает проблему поиска rr афаир. Для того что-бы решить проблему аки:

Код

class base
{
public:

};

class child : public base
{
public:
int m_Data;
}

int main()
{
list<base*> baseList; //<---
}



следует набросать самопальную рефлекцию, в простейшем случае:

Код

class base
{
public:
virtual int get_intProperty(string property_) = 0;
};

class child : public base
{
public:
int m_Data;
virtual int get_intProperty(string property_)
{
   if("m_Data" == property_) return m_Data;
}
};




Это просто ужасно.

Добавлено через 5 минут и 16 секунд
И даже вот так можно исхитритцо:

Код


class base
{
public:
virtual void setValues() = 0;
};

class child : public base
{
public:
  int m_Data;
  virtual void setValues() { m_Data = 3; }
};

int main()
{
base* a = new child();
a->setValues();

child *o = reinterpret_cast<child*>(a);

cout<<o->m_Data;

}




Добавлено через 5 минут и 53 секунды
Теперь тока запихни все это в функтор и радуйся жжизни smile

Автор: bsa 7.6.2008, 21:31
chipset, уж лучше вместо reinterpret_cast использовать dynamic_cast - он хоть 0 возвратит в случае неверного преобразования.

Автор: chipset 7.6.2008, 21:32
Цитата(bsa @  7.6.2008,  11:31 Найти цитируемый пост)
chipset, уж лучше вместо reinterpret_cast использовать dynamic_cast - он хоть 0 возвратит в случае неверного преобразования.

+1

Автор: Rififi 7.6.2008, 21:33
Цитата(chipset @  7.6.2008,  21:10 Найти цитируемый пост)
Метод Rififi не решает проблему поиска rr афаир.

это проблема не поиска, а кривого проектирования.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)