Question on the Boost Preprocessor library

Hi all, This is my first email to this list; please point me out if I done anything wrong in this mail like the title format or etc... I am a newbie to the Boost library. I am really interesting on the usage of the Boost preprocessor library. I would like to archive 1 of the thing but I am not sure whether it is possible with Boost preprocessor library: Converting the binary number to hexadecimal or decimal value Eg: BIN2HEX(011) -> 0x3 or BIN2DEC(011) -> 3 BIN2HEX(1111) -> 0xf or BIN2DEC(1111) -> 15 I had read the C-Template-Metaprogramming-Concepts-Tools-and-Techniques-from-Boost-and- Beyond-C-in-Depth-Series which tell me how to archive that using template. But what I really want is to done it with the preprocessor without using any template which will not affect the run time but only the compile time. I know that I can use the loop and the arithmetic function from the Boost library but how do I get the binary number characters count, eg. COUNT(011) -> 3 or COUNT(0111) -> 4. So that I can use this count with loop and the arithmetic function to perform the conversion from binary to hexadecimal or decimal. Thanks in advance. Regards, Shin Guey

AMDG Wong, Shin Guey wrote:
Hi all,
This is my first email to this list; please point me out if I done anything wrong in this mail like the title format or etc…
I am a newbie to the Boost library. I am really interesting on the usage of the Boost preprocessor library. I would like to archive 1 of the thing but I am not sure whether it is possible with Boost preprocessor library:
Converting the binary number to hexadecimal or decimal value
Eg: BIN2HEX(011) -> 0x3 or BIN2DEC(011) -> 3
BIN2HEX(1111) -> 0xf or BIN2DEC(1111) -> 15
I had read the C-Template-Metaprogramming-Concepts-Tools-and-Techniques-from-Boost-and-Beyond-C-in-Depth-Series which tell me how to archive that using template. But what I really want is to done it with the preprocessor without using any template which will not affect the run time but only the compile time.
I know that I can use the loop and the arithmetic function from the Boost library but how do I get the binary number characters count, eg. COUNT(011) -> 3 or COUNT(0111) -> 4. So that I can use this count with loop and the arithmetic function to perform the conversion from binary to hexadecimal or decimal.
You can't implement BIN2DEC(1111) using Boost.Preprocessor arithmetic. The only way to do it is: #define BIN2DEC_0 0 #define BIN2DEC_1 1 #define BIN2DEC_11 2 ... #define BIN2DEC_1111 15 ... There is a way to get BIN2HEX(1 1 1 1) for example: #include <boost/preprocessor/control/while.hpp> #include <boost/preprocessor/cat.hpp> #include <boost/preprocessor/seq/cat.hpp> #include <boost/preprocessor/facilities/is_empty.hpp> #include <boost/preprocessor/tuple/elem.hpp> #include <boost/preprocessor/logical/not.hpp> #include <boost/preprocessor/dec.hpp> #include <boost/preprocessor/arithmetic/mod.hpp> #include <boost/preprocessor/repetition/repeat.hpp> #include <boost/preprocessor/tuple/eat.hpp> #define BINARY_IS_ONE_IMPL_0 #define BINARY_IS_ONE_IMPL_1 #define BINARY_IS_ONE(x) BOOST_PP_IS_EMPTY(BOOST_PP_CAT(BINARY_IS_ONE_IMPL_, x)) #define BINARY_POP_FRONT_IMPL_0 #define BINARY_POP_FRONT_IMPL_1 #define BINARY_POP_FRONT_IMPL(x) BOOST_PP_CAT(BINARY_POP_FRONT_IMPL_, x) #define BINARY_CLEAR(x) EMPTY_BINARY #define BINARY_POP_FRONT(x) BOOST_PP_IF(BINARY_IS_ONE(x), BINARY_CLEAR, BINARY_POP_FRONT_IMPL)(x) #define BINARY_IS_EMPTY_IMPL_EMPTY_BINARY #define BINARY_IS_EMPTY(x) BOOST_PP_IS_EMPTY(BOOST_PP_CAT(BINARY_IS_EMPTY_IMPL_, x)) #define BINARY_SIZE_IMPL(n, x) (BINARY_POP_FRONT(BOOST_PP_TUPLE_ELEM(2, 0, x)), n) #define BINARY_SIZE_IMPL_PRED(n, x) BOOST_PP_NOT(BINARY_IS_ONE(BOOST_PP_TUPLE_ELEM(2, 0, x))) #define BINARY_SIZE(x) BOOST_PP_TUPLE_ELEM(2, 1, BOOST_PP_WHILE(BINARY_SIZE_IMPL_PRED, BINARY_SIZE_IMPL, (x, 1))) #define BINARY_FRONT_IMPL_0 0, ~ #define BINARY_FRONT_IMPL_1 1, ~ #define BINARY_FRONT_IMPL(x, y) x #define BINARY_FRONT(x) BOOST_PP_CAT(BINARY_FRONT_IMPL, (BOOST_PP_CAT(BINARY_FRONT_IMPL_, x))) #define BINARY_TO_HEX_IMPL_0000 0 #define BINARY_TO_HEX_IMPL_0001 1 #define BINARY_TO_HEX_IMPL_0010 2 #define BINARY_TO_HEX_IMPL_0011 3 #define BINARY_TO_HEX_IMPL_0100 4 #define BINARY_TO_HEX_IMPL_0101 5 #define BINARY_TO_HEX_IMPL_0110 6 #define BINARY_TO_HEX_IMPL_0111 7 #define BINARY_TO_HEX_IMPL_1000 8 #define BINARY_TO_HEX_IMPL_1001 9 #define BINARY_TO_HEX_IMPL_1010 A #define BINARY_TO_HEX_IMPL_1011 B #define BINARY_TO_HEX_IMPL_1100 C #define BINARY_TO_HEX_IMPL_1101 D #define BINARY_TO_HEX_IMPL_1110 E #define BINARY_TO_HEX_IMPL_1111 F #define BINARY_GET1(x) (BINARY_FRONT(x)) #define BINARY_GET2(x) (BINARY_FRONT(x))BINARY_GET1(BINARY_POP_FRONT(x)) #define BINARY_GET3(x) (BINARY_FRONT(x))BINARY_GET2(BINARY_POP_FRONT(x)) #define BINARY_GET4(x) (BINARY_FRONT(x))BINARY_GET3(BINARY_POP_FRONT(x)) #define BINARY_EVAL(x) x #define BINARY_EMPTY #define BINARY_POP1(x) BINARY_EVAL(BINARY_POP_FRONT BINARY_EMPTY(x)) #define BINARY_POP2(x) BINARY_POP1(BINARY_POP_FRONT(x)) #define BINARY_POP3(x) BINARY_POP2(BINARY_POP_FRONT(x)) #define BINARY_POP4(x) BINARY_POP3(BINARY_POP_FRONT(x)) #define BINARY_TO_HEX_IMPL(n, result) (BINARY_POP4(BOOST_PP_TUPLE_ELEM(2, 0, result)), BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(2, 1, result), BOOST_PP_CAT(BINARY_TO_HEX_IMPL_, BOOST_PP_SEQ_CAT(BINARY_GET4(BOOST_PP_TUPLE_ELEM(2, 0, result)))))) #define BINARY_RESULT(n, result) /**/ #define BINARY_TO_HEX_IMPL_SHORT_CIRCUIT(n, result) BOOST_PP_IF(BINARY_TO_HEX_PRED(n, result), BINARY_TO_HEX_IMPL, BINARY_RESULT)(n, result) #define BINARY_TO_HEX_PRED(n, x) BOOST_PP_NOT(BINARY_IS_EMPTY(BOOST_PP_TUPLE_ELEM(2, 0, x))) #define BINARY_PAD_TO_4(x) BOOST_PP_REPEAT(BOOST_PP_MOD(BOOST_PP_SUB(4, BOOST_PP_MOD(BINARY_SIZE(x), 4)), 4), 0 BOOST_PP_TUPLE_EAT(3), ~) x #define BINARY_TO_HEX(val) BOOST_PP_TUPLE_ELEM(2, 1, BOOST_PP_WHILE(BINARY_TO_HEX_PRED, BINARY_TO_HEX_IMPL_SHORT_CIRCUIT, (BINARY_PAD_TO_4(val), 0x))) BINARY_TO_HEX(1 0 1 0 0 1) In Christ, Steven Watanabe

Hello Sorry, I have several questions on C++ instead of any boost library. But I believe the boost guys could easily give me help. :-) 1) I found code fragment like this, esp. in macro definitions: do { \ \ // ... \ } while(0) Why is the do/while clause needed here? 2) I found large amount of code like this in a class implementation: AClass::func() { this->func1(); } Why is 'this->' needed? Thanks for any help. B/Rgds Max

boost_www wrote:
1) I found code fragment like this, esp. in macro definitions:
do { \ \ // ... \ } while(0)
Why is the do/while clause needed here?
That's a macro idiom that dates back to classic C. It packages a compound statement { stmt1; stmt2; } as if it were a single statement. If you write #define YOURMACRO(arg) { stmt1; stmt2; } and a subsequent coder writes this: if (some_condition) YOURMACRO(1); else std::cout << "Whoops, error.\n"; he or she will get a nasty surprise. It works to drop the semicolon after YOURMACRO(1), but that imposes a new requirement: some macros must be followed by semicolons, others must NOT be followed by semicolons, and the coder must know something about the macro's implementation to use it correctly. If you write #define YOURMACRO(arg) do { stmt1; stmt2; } while (0) then it's appropriate (required) to write a semicolon after the macro invocation, and subsequent coders can do that consistently without needing to know which kind of macro this is.
2) I found large amount of code like this in a class implementation:
AClass::func() { this->func1(); }
Why is 'this->' needed?
There are a few different reasons. 1. Some people write that as a stylistic preference, since it clarifies that you're referencing a data member rather than a local variable. 2. In some IDEs, when you write "this->", the IDE pops up a list of members from which to choose. 3. In some arcane scenarios such as a template subclass derived from a template base class, the language sometimes requires this->baseClassMember (though I believe MSVC still permits a plain baseClassMember reference as an extension). But if you ask any more such questions on this list, the moderator might yell at both of us. ;-)

hello Nat, Thanks you very much for your explanation! for 1), I never heard of that idiom. In fact, after playing with C++ for more thant 10 years, I am still keeping finding interesting corners of the language. :) What I get from your information is that, the do/while clause is a MUST-HAVE and is obviously intentional. for 2), it seems that 'this->' is a question of coding style and generally we could omit it. I really appreciate your help! and I believe the moderator of the list will not yell to us for such topic. :-) B/Rgds Max
1) I found code fragment like this, esp. in macro definitions:
do { \ \ // ... \ } while(0)
Why is the do/while clause needed here?
That's a macro idiom that dates back to classic C. It packages a compound statement { stmt1; stmt2; } as if it were a single statement. If you write #define YOURMACRO(arg) { stmt1; stmt2; } and a subsequent coder writes this: if (some_condition) YOURMACRO(1); else std::cout << "Whoops, error.\n"; he or she will get a nasty surprise. It works to drop the semicolon after YOURMACRO(1), but that imposes a new requirement: some macros must be followed by semicolons, others must NOT be followed by semicolons, and the coder must know something about the macro's implementation to use it correctly. If you write #define YOURMACRO(arg) do { stmt1; stmt2; } while (0) then it's appropriate (required) to write a semicolon after the macro invocation, and subsequent coders can do that consistently without needing to know which kind of macro this is.
2) I found large amount of code like this in a class implementation:
AClass::func() { this->func1(); }
Why is 'this->' needed?
There are a few different reasons. 1. Some people write that as a stylistic preference, since it clarifies that you're referencing a data member rather than a local variable. 2. In some IDEs, when you write "this->", the IDE pops up a list of members from which to choose. 3. In some arcane scenarios such as a template subclass derived from a template base class, the language sometimes requires this->baseClassMember (though I believe MSVC still permits a plain baseClassMember reference as an extension). But if you ask any more such questions on this list, the moderator might yell at both of us. ;-) _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org

At 9:47 AM +0800 7/17/08, boost_www wrote:
hello Nat,
Thanks you very much for your explanation!
for 1), I never heard of that idiom. In fact, after playing with C++ for more thant 10 years, I am still keeping finding interesting corners of the language. :)
What I get from your information is that, the do/while clause is a MUST-HAVE and is obviously intentional.
Absolutely.
for 2), it seems that 'this->' is a question of coding style and generally we could omit it.
Generally, but not always. If you want to call a member function (_especially_ in templated/library code), then you should qualify it with "this->", because you don't know if there will be a function named "func1" available when the code is compiled. -- -- Marshall Marshall Clow Idio Software <mailto:marshall@idio.com> It is by caffeine alone I set my mind in motion. It is by the beans of Java that thoughts acquire speed, the hands acquire shaking, the shaking becomes a warning. It is by caffeine alone I set my mind in motion.

Hello Marshall Thanks. With your additional point, the things are getting more clearer. B/Rgds Max ----- Original Message ---- From: Marshall Clow To: boost-users@lists.boost.org Sent: 2008-07-17 10:26:23 Subject: Re: [Boost-users] Several questions on C++
At 9:47 AM +0800 7/17/08, boost_www wrote:
hello Nat,
Thanks you very much for your explanation!
for 1), I never heard of that idiom. In fact, after playing with C++ for more thant 10 years, I am still keeping finding interesting corners of the language. :)
What I get from your information is that, the do/while clause is a MUST-HAVE and is obviously intentional.
Absolutely.
for 2), it seems that 'this->' is a question of coding style and generally we could omit it.
Generally, but not always. If you want to call a member function (_especially_ in templated/library code), then you should qualify it with "this->", because you don't know if there will be a function named "func1" available when the code is compiled. -- -- Marshall Marshall Clow Idio Software <mailto:marshall@idio.com> It is by caffeine alone I set my mind in motion. It is by the beans of Java that thoughts acquire speed, the hands acquire shaking, the shaking becomes a warning. It is by caffeine alone I set my mind in motion. _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org

1) I found code fragment like this, esp. in macro definitions:
do { \ \ // ... \ } while(0)
Why is the do/while clause needed here?
Probably so the statements inside the do...while are in their own block, with its own scope. If simple curly braces were used, then sometimes it would break 'if' statements in a weird way, so using do {} while(0) is more robust. Example: #define FOO { ... } if (cond) FOO; //<--- breaks else FOO;
2) I found large amount of code like this in a class implementation:
AClass::func() { this->func1(); }
Why is 'this->' needed?
Probably because the class is a template with a template base class, so explicitly using this-> is one way to make sure that g++ recognizes func1 as an inheritted member function. Another possiblity is that typeing '->' triggers the autocomplete function in some editors, so typing 'this->' provides them with a convenient way to recall & type the correct function name within the scope of 'this'.

Hello John Also many thanks to you for your explanation. B/Rgds Max ----- Original Message ---- From: John Femiani To: boost-users@lists.boost.org Sent: 2008-07-17 01:36:03 Subject: Re: [Boost-users] Several questions on C++
1) I found code fragment like this, esp. in macro definitions:
do { \ \ // ... \ } while(0)
Why is the do/while clause needed here?
Probably so the statements inside the do...while are in their own block, with its own scope. If simple curly braces were used, then sometimes it would break 'if' statements in a weird way, so using do {} while(0) is more robust. Example: #define FOO { ... } if (cond) FOO; //<--- breaks else FOO;
2) I found large amount of code like this in a class implementation:
AClass::func() { this->func1(); }
Why is 'this->' needed?
Probably because the class is a template with a template base class, so explicitly using this-> is one way to make sure that g++ recognizes func1 as an inheritted member function. Another possiblity is that typeing '->' triggers the autocomplete function in some editors, so typing 'this->' provides them with a convenient way to recall & type the correct function name within the scope of 'this'. _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org

Wong, Shin Guey a écrit :
I had read the C-Template-Metaprogramming-Concepts-Tools-and-Techniques-from-Boost-and-Beyond-C-in-Depth-Series which tell me how to archive that using template. But what I really want is to done it with the preprocessor without using any template which will not affect the run time but only the compile time.
You are aware that tempalte meta-programming WILL result in compile-time expansion fo the resulting constant do you ? Why did you reject this solution ?
participants (8)
-
boost_www
-
Joel Falcou
-
John Femiani
-
Marshall Clow
-
Max
-
Nat Goodspeed
-
Steven Watanabe
-
Wong, Shin Guey