
OK, I know BOOST_FOREACH isn't part of the official (1.33.1) build yet, but hopefully some people here are using this excellent algorithm and can help me out... (note that I am using MS Visual Studio 2005): How can I use BOOST_FOREACH to iterate through a map? For example, the following won't build: std::map<int, int> m; BOOST_FOREACH(std::pair<int, int> p, m) { } I get the following error: warning C4002: too many actual parameters for macro 'BOOST_FOREACH' However, the following will work OK: std::map<int, int> m; std::pair<int, int> p; BOOST_FOREACH(p, m) { } But is there a way to declare the pair within the FOREACH loop? Note that I also tried the following, with no success: std::map<int, int> m; BOOST_FOREACH(std::map<int, int>::value_type p, m) { } A typedef also seems to work, e.g.: std::map<int, int> m; typedef std::pair<int, int> mpair; BOOST_FOREACH(mpair p, m) { } Can the pair be declared without a typedef? Is this a limitation of the MS compiler? Thanks in advance.

Rob Caldecott wrote:
OK, I know BOOST_FOREACH isn't part of the official (1.33.1) build yet, but hopefully some people here are using this excellent algorithm and can help me out... (note that I am using MS Visual Studio 2005):
How can I use BOOST_FOREACH to iterate through a map? For example, the following won't build:
std::map<int, int> m; BOOST_FOREACH(std::pair<int, int> p, m) { }
I get the following error:
warning C4002: too many actual parameters for macro 'BOOST_FOREACH'
This is covered in the docs: http://tinyurl.com/l72gp Your solutions (pre-declare the loop variable or use a typedef) are the way to go. -- Eric Niebler Boost Consulting www.boost-consulting.com

On Mon, September 18, 2006 12:52 pm, Rob Caldecott wrote:
Can the pair be declared without a typedef? Is this a limitation of the MS compiler?
It is a limitation of the preprocessor. It does not recognize <> as any sort of parentheses, so it thinks the , separating the template parameters is a macro argument separator. You can try wrapping the whole argument in parentheses: BOOST_FOREACH((std::pair<int, int> p), m) But I'm not sure if the PP passes the parentheses on - in that case, you might get syntax errors in the generated code. If that's the case, you'll have to use the typedef.

Sebastian Redl writes:
On Mon, September 18, 2006 12:52 pm, Rob Caldecott wrote:
Can the pair be declared without a typedef? Is this a limitation of the MS compiler?
It is a limitation of the preprocessor. It does not recognize <> as any sort of parentheses, so it thinks the , separating the template parameters is a macro argument separator.
You can try wrapping the whole argument in parentheses: BOOST_FOREACH((std::pair<int, int> p), m)
But I'm not sure if the PP passes the parentheses on - in that case, you might get syntax errors in the generated code. If that's the case, you'll have to use the typedef.
I've done something like this: #include "boost/tuple/tuple.hpp" #define FOREACH_PAIR( KEY, VAL, COL) FOREACH (boost::tie(KEY,VAL),COL) // and then, for example int key, value; FOREACH_PAIR(key, value m); It's not perfect; specfically, I don't think that you can write into the map this way. I suspect there _is_ a way for that to work, I just haven't figured it out yet. :-) I'd like the eventual "official" FOREACH to have some additional variations like this... ---------------------------------------------------------------------- Dave Steffen, Ph.D. Software Engineer IV Disobey this command! Numerica Corporation - Douglas Hofstadter dgsteffen at numerica dot us

Dave Steffen wrote:
Sebastian Redl writes:
On Mon, September 18, 2006 12:52 pm, Rob Caldecott wrote:
Can the pair be declared without a typedef? Is this a limitation of the MS compiler?
It is a limitation of the preprocessor. It does not recognize <> as any sort of parentheses, so it thinks the , separating the template parameters is a macro argument separator.
You can try wrapping the whole argument in parentheses: BOOST_FOREACH((std::pair<int, int> p), m)
But I'm not sure if the PP passes the parentheses on - in that case, you might get syntax errors in the generated code. If that's the case, you'll have to use the typedef.
I've done something like this:
#include "boost/tuple/tuple.hpp"
#define FOREACH_PAIR( KEY, VAL, COL) FOREACH (boost::tie(KEY,VAL),COL)
// and then, for example
int key, value;
FOREACH_PAIR(key, value m);
It's not perfect; specfically, I don't think that you can write into the map this way. I suspect there _is_ a way for that to work, I just haven't figured it out yet. :-)
I'd like the eventual "official" FOREACH to have some additional variations like this...
Boost.Parameter(cvs head) seems to already have a workaround for it. #include <boost/parameter/aux_/parenthesized_type.hpp> #define UNPARENTHESIZE BOOST_PARAMETER_PARENTHESIZED_TYPE int main() { std::map<int, int> m; BOOST_FOREACH ( UNPARENTHESIZE((std::pair<int, int>)) p, m ) { } } -- Shunsuke Sogame
participants (5)
-
Dave Steffen
-
Eric Niebler
-
Rob Caldecott
-
Sebastian Redl
-
Shunsuke Sogame