Je n'aimais pas l'idée d'être obligé d'ajouter typedefs chaque fois que je voulais utiliser un foreach sur une carte. Voici donc ma mise en œuvre sur la base du code foreach boost:
#ifndef MUNZEKONZA_FOREACH_IN_MAP
#include <boost/preprocessor/cat.hpp>
#define MUNZEKONZA_FOREACH_IN_MAP_ID(x) BOOST_PP_CAT(x, __LINE__)
namespace munzekonza {
namespace foreach_in_map_private {
inline bool set_false(bool& b) {
b = false;
return false;
}
}
}
#define MUNZEKONZA_FOREACH_IN_MAP(key, value, map) \
for(auto MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it) = map.begin(); \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it) != map.end();) \
for(bool MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue) = true; \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue) && \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it) != map.end(); \
(MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue)) ? \
((void)++MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it)) : \
(void)0) \
if(munzekonza::foreach_in_map_private::set_false( \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue))) {} else \
for(key = MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it)->first; \
!MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue); \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue) = true) \
if(munzekonza::foreach_in_map_private::set_false( \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue))) {} else \
for(value = MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_it)->second; \
!MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue); \
MUNZEKONZA_FOREACH_IN_MAP_ID(_foreach_in_map_continue) = true)
Ensuite, vous pouvez l'utiliser dans votre code: #define foreach_in_map MUNZEKONZA_FOREACH_IN_MAP
std::map<int, std::string> mymap;
mymap[0] = "oi";
mymap[1] = "noi";
std::map<int, std::string> newmap;
foreach_in_map(int key, const std::string& value, mymap) {
newmap[key] = value;
}
ASSERT_EQ(newmap.size(), 2);
ASSERT_EQ(newmap.count(0), 1);
ASSERT_EQ(newmap.count(1), 1);
ASSERT_EQ(newmap.at(0), "oi");
ASSERT_EQ(newmap.at(1), "noi");
Vous pouvez également modifier les valeurs: #define foreach_in_map MUNZEKONZA_FOREACH_IN_MAP
std::map<int, std::string> mymap;
mymap[0] = "oi";
mymap[1] = "noi";
std::map<int, std::string> newmap;
foreach_in_map(int key, std::string& value, mymap) {
value = "voronoi" + boost::lexical_cast<std::string>(key);
}
ASSERT_EQ(mymap.size(), 2);
ASSERT_EQ(mymap.count(0), 1);
ASSERT_EQ(mymap.count(1), 1);
ASSERT_EQ(mymap.at(0), "voronoi0");
ASSERT_EQ(mymap.at(1), "voronoi1");
Ce n'est pas exactement un double, mais voir ici: http://stackoverflow.com/questions/461507/how-to-use-boostforeach-with-a-boostptrmap/461908 # 461908 –