![]() |
|
|
|
#31 |
|
Eric Sosman <> writes:
>Andrey Vul wrote: >>[...] >>Think of what I'm trying to do as factorial via preprocessor (i.e. the >>expansion of f(5) would be (5*(4*(3*(2*(1))))) ,but how do you tail >>decrement and recurse properly? >You don't. You google. http://google.to/search?q=factorial+preprocessor Stefan Ram |
|
|
|
|
#32 |
|
Posts: n/a
|
Eric Sosman <> writes:
>>http://google.to/search?q=factorial+preprocessor >I suspect you intended the first of them, but it's not C. http://bannalia.blogspot.com/2008/10...recursion.html is C and shows how to implement tail recursion, which is sufficient to implement the factorial, but not arbitrary (non-tail) recursion. Yes, it uses boost, but the preprocessor part of boost should be the same for C and C++. The solution shown there will run only for small argument values under many implementations. My solution would be: #define FACTORIAL0 1 #define FACTORIAL1 1 #define FACTORIAL2 2 #define FACTORIAL3 6 #define FACTORIAL4 24 #define FACTORIAL5 120 #define FACTORIAL6 720 #define FACTORIAL7 5040 #define FACTORIAL8 40320 #define FACTORIAL9 362880 #define FACTORIAL10 3628800 #define FACTORIAL11 39916800 #define FACTORIAL12 479001600 #define FACTORIAL13 6227020800 #define FACTORIAL14 87178291200 #define FACTORIAL15 1307674368000 #define FACTORIAL16 20922789888000 #define FACTORIAL17 355687428096000 #define FACTORIAL18 6402373705728000 #define FACTORIAL19 121645100408832000 #define FACTORIAL20 2432902008176640000 #define FACTORIAL21 51090942171709440000 #define FACTORIAL22 1124000727777607680000 #define FACTORIAL23 25852016738884976640000 #define FACTORIAL24 620448401733239439360000 #define FACTORIAL25 15511210043330985984000000 #define FACTORIAL26 403291461126605635584000000 #define FACTORIAL27 10888869450418352160768000000 #define FACTORIAL28 304888344611713860501504000000 #define FACTORIAL29 8841761993739701954543616000000 #define FACTORIAL30 265252859812191058636308480000000 #define FACTORIAL(x) FACTORIAL##x Stefan Ram |
|
|
|
#33 |
|
Posts: n/a
|
"Stefan Ram" <> wrote in message
news:factorial-... > Eric Sosman <> writes: >>>http://google.to/search?q=factorial+preprocessor >>I suspect you intended the first of them, but it's not C. > > http://bannalia.blogspot.com/2008/10...recursion.html > > is C and shows how to implement tail recursion, > which is sufficient to implement the factorial, > but not arbitrary (non-tail) recursion. > > Yes, it uses boost, but the preprocessor part of > boost should be the same for C and C++. > > The solution shown there will run only for small > argument values under many implementations. > > My solution would be: [...] > #define FACTORIAL(x) FACTORIAL##x FWIW, this does not work when x is a token: __________________________________________________ _____ int main(void) { #define N 4 printf("%lu\n", FACTORIAL(N)); return 0; } __________________________________________________ _____ You need an extra level of expansion: #define CONCATX(t1, t2)t1##t2 #define CONCAT(t1, t2)CONCATX(t1, t2) #define FACTORIAL(x) CONCAT(FACTORIAL, x) Chris M. Thomasson |
|
|
|
#34 |
|
Posts: n/a
|
On Oct 28, 4:45*pm, Andrey Vul <andrey....@gmail.com> wrote:
> Is there a way to do this: > cat << "EOF" | cpp -Dn=2 - > #define d define > d foo#(n-1) (n-1) > EOF > > with the output being > #define foo1 1 > > ? No. Ignoring the problems with the macro definition itself, the preprocessor doesn't evaluate arithmetic expressions like that. Assuming that the # operator worked like that (it doesn't), the result would look more like #define foo(2-1) (2-1) The preprocessor does text substitution. Period. It doesn't understand expressions or arithmetic or anything like that. John Bode |
|
|
|
#35 |
|
Posts: n/a
|
John Bode <> writes:
> On Oct 28, 4:45Â*pm, Andrey Vul <andrey....@gmail.com> wrote: >> Is there a way to do this: >> cat << "EOF" | cpp -Dn=2 - >> #define d define >> d foo#(n-1) (n-1) >> EOF >> >> with the output being >> #define foo1 1 >> >> ? > > No. > > Ignoring the problems with the macro definition itself, the > preprocessor doesn't evaluate arithmetic expressions like that. > Assuming that the # operator worked like that (it doesn't), the result > would look more like > > #define foo(2-1) (2-1) > > The preprocessor does text substitution. Period. It doesn't > understand expressions or arithmetic or anything like that. It doesn't understand arithmetic expressions in macro expansions, which is what the OP would need. It does understand them in #if directives. For example, this program: #include <stdio.h> int main(void) { #if 2 + 2 == 4 puts("ok"); #endif #if 2 + 2 == 5 puts("OOPS"); #endif return 0; } prints "ok". -- Keith Thompson (The_Other_Keith) kst- <http://www.ghoti.net/~kst> Nokia "We must do something. This is something. Therefore, we must do this." -- Antony Jay and Jonathan Lynn, "Yes Minister" Keith Thompson |
|
|
|
#36 |
|
Posts: n/a
|
Andrey Vul <> wrote:
> On Oct 28, 10:42=A0pm, Eric Sosman <esos...@ieee-dot-org.invalid> wrote: > > Andrey Vul wrote: > > > > I'm asking if there's a way to force cpp to _not_ linklist #define > > > chains. > > > > =A0 =A0 =A0Yes: Just use it as it stands; there are no chains or lists > > of definitions. =A0See 6.10.3.4. > > Multi-pass somehow registers with me as linked lists. My bad. > But 6.10.3.4 is what I'm trying to subvert. Well, _don't_. It's the wrong thing to want. It's not what the C preprocessor was designed for, and trying to subvert that is like trying to make a car go directly sideways: it's not normally possible, and even when, with a great deal of dirty hackery, you manage to do it anyway in one specific instance, you'll still end up with the steering wheel in the wrong place and the car wider than the lane. Richard Richard Bos |
|
|
|
#37 |
|
Posts: n/a
|
On Oct 28, 10:41*pm, Seebs <usenet-nos...@seebs.net> wrote:
> On 2009-10-29, Andrey Vul <andrey....@gmail.com> wrote: > > > > #define I #ifndef > > #define D #define > > #define E #endif > > Don't do this. I'm using that in order to prevent premature #ifndef evaluation. Andrey Vul |
|
|
|
#38 |
|
Posts: n/a
|
On 2009-11-03, Andrey Vul <> wrote:
> On Oct 28, 10:41*pm, Seebs <usenet-nos...@seebs.net> wrote: >> On 2009-10-29, Andrey Vul <andrey....@gmail.com> wrote: >> > #define I #ifndef >> > #define D #define >> > #define E #endif >> Don't do this. > I'm using that in order to prevent premature #ifndef evaluation. That is not how cpp works. Even if it were, it would not be a sane way to try to do this. If you find yourself trying to outsmart the preprocessor, stop. Go do something else -- say, write a program to generate the code you want. -s -- Copyright 2009, all wrongs reversed. Peter Seebach / usenet- http://www.seebs.net/log/ <-- lawsuits, religion, and funny pictures http://en.wikipedia.org/wiki/Fair_Game_(Scientology) <-- get educated! Seebs |
|
|
|
#39 |
|
Posts: n/a
|
Andrey Vul wrote:
> On Oct 28, 10:41 pm, Seebs <usenet-nos...@seebs.net> wrote: >> On 2009-10-29, Andrey Vul <andrey....@gmail.com> wrote: >> >> >>> #define I #ifndef >>> #define D #define >>> #define E #endif >> Don't do this. > > I'm using that in order to prevent premature #ifndef evaluation. No, you're using it to cause syntax errors. (Not entirely true: You can avoid syntax errors by defining the macros as shown and then never expanding any of them ...) For example, if you try to use the D macro like this: D FOO bar you will get an expansion that might be represented as # define FOO bar but this expansion will *not* be a preprocessor directive. Macro replacement never generates a preprocessor directive, even if it generates a sequence that resembles one (6.10.3.4p3). So what you've got is the four tokens #,define,FOO,bar surviving *after* the preprocessor has finished its work, and that sequence of tokens does not match any part of any production of C's grammar. (Trivial proof: # can be a preprocessing token, but it cannot be a token.) Hence, you get a syntax error. You could "use" your macros in `#ifdef D' and `#ifndef I' and `#if defined(E)' and so on, but that's all. Expand any of them, and you're toast. Heed Seebs' advice. -- Eric Sosman lid Eric Sosman |
|
|
|
#40 |
|
Posts: n/a
|
On Nov 3, 8:48*am, Eric Sosman <esos...@ieee-dot-org.invalid> wrote:
> * * *For example, if you try to use the D macro like this: > > * * * * D FOO bar > > you will get an expansion that might be represented as > > * * * * # define FOO bar > > but this expansion will *not* be a preprocessor directive. *Macro > replacement never generates a preprocessor directive. I know that. But cpp foo.c -DD=#define | cpp will give the intended result. The magic token is shell-piping what looks like a directive into an actual directive. Andrey Vul |
|