Alternatives to #define?

Discussion in 'C++' started by Carl Ribbegaardh, Jul 2, 2004.

  1. What other c++ constructs can I use instead of #define for executing a
    couple of functions?
    Example:

    #define DO_STUFF doThis(); doThat();

    I'd guess that I can either use a template function, an inlined function or
    an inlined static method.

    //1
    namespace MyUtils
    {
    template<>
    void doStuff()
    {
    doThis();
    doThat();
    }
    }

    //2
    namespace MyUtils
    {
    inline void doStuff()
    {
    doThis();
    doThat();
    }
    }

    //3
    class MyUtils
    {
    public:
    static inline void doStuff() const
    {
    doThis();
    doThat();
    }
    }

    I *believe* that the template version always is inlined, and that the other
    2 versions is probably inlined.
    Are theese approaches correct?
    Which should be preferred?
    Are there any other better way?

    /Carl
     
    Carl Ribbegaardh, Jul 2, 2004
    #1
    1. Advertising

  2. "Carl Ribbegaardh" <> wrote in message
    news:...
    > What other c++ constructs can I use instead of #define for executing a
    > couple of functions?
    > Example:
    >
    > #define DO_STUFF doThis(); doThat();
    >
    > I'd guess that I can either use a template function, an inlined function

    or
    > an inlined static method.
    >
    > //1
    > namespace MyUtils
    > {
    > template<>
    > void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }
    >
    > //2
    > namespace MyUtils
    > {
    > inline void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }
    >
    > //3
    > class MyUtils
    > {
    > public:
    > static inline void doStuff() const
    > {
    > doThis();
    > doThat();
    > }
    > }
    >
    > I *believe* that the template version always is inlined, and that the

    other
    > 2 versions is probably inlined.


    No that is not true. I guess you are thinking of the exception that
    templates have from the normal one definition rules for functions and
    classes. But that's an entirely seperate issue.

    > Are theese approaches correct?


    They are all correct.

    > Which should be preferred?


    The second

    > Are there any other better way?


    What's wrong with the second method? Why is it even an issue?

    john
     
    John Harrison, Jul 2, 2004
    #2
    1. Advertising

  3. "John Harrison" <> wrote in message
    news:...
    >
    > "Carl Ribbegaardh" <> wrote in message
    > news:...
    > > What other c++ constructs can I use instead of #define for executing a
    > > couple of functions?
    > > Example:
    > >
    > > #define DO_STUFF doThis(); doThat();
    > >
    > > I'd guess that I can either use a template function, an inlined function

    > or
    > > an inlined static method.
    > >
    > > //1
    > > namespace MyUtils
    > > {
    > > template<>
    > > void doStuff()
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }
    > >
    > > //2
    > > namespace MyUtils
    > > {
    > > inline void doStuff()
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }
    > >
    > > //3
    > > class MyUtils
    > > {
    > > public:
    > > static inline void doStuff() const
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }
    > >
    > > I *believe* that the template version always is inlined, and that the

    > other
    > > 2 versions is probably inlined.

    >
    > No that is not true. I guess you are thinking of the exception that
    > templates have from the normal one definition rules for functions and
    > classes. But that's an entirely seperate issue.
    >
    > > Are theese approaches correct?

    >
    > They are all correct.
    >
    > > Which should be preferred?

    >
    > The second
    >
    > > Are there any other better way?

    >
    > What's wrong with the second method? Why is it even an issue?
    >


    The issue is that I dont *know*.
    I'm currently just guessing/believing. :)

    So the 1st version isn't inlined? Why I thought it would be, is that I've
    read lines like "templates are inlined by definition" but I might have
    interpreted/read/remembered it wrong. Any elaboration on why or why not
    would be much appreciated.

    Thanks! :)
     
    Carl Ribbegaardh, Jul 2, 2004
    #3
  4. "Carl Ribbegaardh" <>
    wrote in message news:...
    >
    > "John Harrison" <> wrote in message
    > news:...
    > >
    > > "Carl Ribbegaardh" <> wrote in

    message
    > > news:...
    > > > What other c++ constructs can I use instead of #define for executing a
    > > > couple of functions?
    > > > Example:
    > > >
    > > > #define DO_STUFF doThis(); doThat();
    > > >
    > > > I'd guess that I can either use a template function, an inlined

    function
    > > or
    > > > an inlined static method.
    > > >
    > > > //1
    > > > namespace MyUtils
    > > > {
    > > > template<>
    > > > void doStuff()
    > > > {
    > > > doThis();
    > > > doThat();
    > > > }
    > > > }
    > > >
    > > > //2
    > > > namespace MyUtils
    > > > {
    > > > inline void doStuff()
    > > > {
    > > > doThis();
    > > > doThat();
    > > > }
    > > > }
    > > >
    > > > //3
    > > > class MyUtils
    > > > {
    > > > public:
    > > > static inline void doStuff() const
    > > > {
    > > > doThis();
    > > > doThat();
    > > > }
    > > > }
    > > >
    > > > I *believe* that the template version always is inlined, and that the

    > > other
    > > > 2 versions is probably inlined.

    > >
    > > No that is not true. I guess you are thinking of the exception that
    > > templates have from the normal one definition rules for functions and
    > > classes. But that's an entirely seperate issue.
    > >
    > > > Are theese approaches correct?

    > >
    > > They are all correct.
    > >
    > > > Which should be preferred?

    > >
    > > The second
    > >
    > > > Are there any other better way?

    > >
    > > What's wrong with the second method? Why is it even an issue?
    > >

    >
    > The issue is that I dont *know*.
    > I'm currently just guessing/believing. :)
    >


    Well method two is using one function to call two others. It's perfectly
    common programming to solve a common problem. The other methods introduce
    extra language features to create a more complex solution to a simple
    problem.

    > So the 1st version isn't inlined? Why I thought it would be, is that I've
    > read lines like "templates are inlined by definition" but I might have
    > interpreted/read/remembered it wrong. Any elaboration on why or why not
    > would be much appreciated.
    >


    If you read that it was wrong. As I said I think you might have read that
    template functions usually go in header files which makes them a little like
    inline functions (which also usually go in header files), but this is for
    technical issues to do with how templates are compiled. It has nothing to do
    with whether the template function call itself is inlined.

    john
     
    John Harrison, Jul 2, 2004
    #4
  5. Carl Ribbegaardh

    Rolf Magnus Guest

    Carl Ribbegaardh wrote:

    > What other c++ constructs can I use instead of #define for executing a
    > couple of functions?
    > Example:
    >
    > #define DO_STUFF doThis(); doThat();
    >
    > I'd guess that I can either use a template function, an inlined
    > function or an inlined static method.
    >
    > //1
    > namespace MyUtils
    > {
    > template<>
    > void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }


    What's that template good for? Actually, I don't think this is valid,
    since it doesn't have any template parameters.

    > //2
    > namespace MyUtils
    > {
    > inline void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }
    >
    > //3
    > class MyUtils
    > {
    > public:
    > static inline void doStuff() const
    > {
    > doThis();
    > doThat();
    > }
    > }


    That's incorrect. You cannot make a static member function const, as
    that wouldn't make sense. Making a member function const means that it
    can be called on const objects, but a static member function isn't
    called on any object at all.

    > I *believe* that the template version always is inlined, and that the
    > other 2 versions is probably inlined.


    No. The template might be inlined or it might not, just like any other
    function.
     
    Rolf Magnus, Jul 2, 2004
    #5
  6. "Carl Ribbegaardh" <> wrote:

    > #define DO_STUFF doThis(); doThat();


    I actually like that. Simple, direct, ALWAYS inlined.

    > namespace MyUtils
    > {
    > template<>
    > void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }


    I tried compiling that, got "Error: non-template
    used as template."

    > namespace MyUtils
    > {
    > inline void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    > }


    That works, and most C++ purists would recommend it,
    but I think it sucks. Too complicated. KISS.
    Use the macro instead.

    > class MyUtils
    > {
    > public:
    > static inline void doStuff() const
    > {
    > doThis();
    > doThat();
    > }
    > }


    "error: static member function `static void MyUtils::doStuff()'
    cannot have `const' method qualifier"

    Why stir up trouble with complicated stuff when trying to
    solve a simple problem? Usually the simpliest workable
    solution is the best. Sometimes a macro is the thing that fits
    that bill.


    --
    Cheers,
    Robbie Hatley
    Tustin, CA, USA
    email: lonewolfintj at pacbell dot net
    web: home dot pacbell dot net slant earnur slant










    ----== Posted via Newsfeed.Com - Unlimited-Uncensored-Secure Usenet News==----
    http://www.newsfeed.com The #1 Newsgroup Service in the World! >100,000 Newsgroups
    ---= 19 East/West-Coast Specialized Servers - Total Privacy via Encryption =---
     
    Robbie Hatley, Jul 3, 2004
    #6
  7. "Robbie Hatley" <lonewolfintj at pacbell dot net> wrote in message
    news:40e655f9_2@127.0.0.1...
    > "Carl Ribbegaardh" <> wrote:
    >
    > > #define DO_STUFF doThis(); doThat();

    >
    > I actually like that. Simple, direct, ALWAYS inlined.
    >
    > > namespace MyUtils
    > > {
    > > template<>
    > > void doStuff()
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }

    >
    > I tried compiling that, got "Error: non-template
    > used as template."


    Yes, I just wrote it in the news reader. Think of it as pseudo code ;)

    >
    > > namespace MyUtils
    > > {
    > > inline void doStuff()
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }

    >
    > That works, and most C++ purists would recommend it,
    > but I think it sucks. Too complicated. KISS.
    > Use the macro instead.
    >
    > > class MyUtils
    > > {
    > > public:
    > > static inline void doStuff() const
    > > {
    > > doThis();
    > > doThat();
    > > }
    > > }

    >
    > "error: static member function `static void MyUtils::doStuff()'
    > cannot have `const' method qualifier"
    >


    Yes, the const should probably go away. It's also just invented on the fly
    to show roughly how I thought. Pseudo code ;)

    > Why stir up trouble with complicated stuff when trying to
    > solve a simple problem? Usually the simpliest workable
    > solution is the best. Sometimes a macro is the thing that fits
    > that bill.
    >


    But macros can be difficult to follow too. This example is very simplistic,
    but for example logging macros and testing macros can be difficult to read
    and maintain. But I do like how the compiler has an opportunity to remove
    large parts of the code by switching a compiler flag.

    I'm just interested in learning different techniques of performing the same
    task, just to improve my toolbox :)

    Thanks!
    /Carl

    >
    > --
    > Cheers,
    > Robbie Hatley
    > Tustin, CA, USA
    > email: lonewolfintj at pacbell dot net
    > web: home dot pacbell dot net slant earnur slant
    >
    >
    >
    >
    >
    >
    >
    >
    >
    >
    > ----== Posted via Newsfeed.Com - Unlimited-Uncensored-Secure Usenet

    News==----
    > http://www.newsfeed.com The #1 Newsgroup Service in the World! >100,000

    Newsgroups
    > ---= 19 East/West-Coast Specialized Servers - Total Privacy via Encryption

    =---
     
    Carl Ribbegaardh, Jul 3, 2004
    #7
  8. just use this.

    >>>namespace MyUtils
    >>>{
    >>> inline void doStuff()
    >>> {
    >>> doThis();
    >>> doThat();
    >>> }
    >>>}

    >>
    >>That works, and most C++ purists would recommend it,
    >>but I think it sucks. Too complicated. KISS.
    >>Use the macro instead.


    this is probably the most bizarre thing i've read in a while. it works,
    huh?:

    for (int i = 0; i < 10; ++i)
    STUFF

    vs.

    for (int i = 0; i < 10; ++i)
    doStuff();

    "kiss" that.

    > But macros can be difficult to follow too. This example is very simplistic,
    > but for example logging macros and testing macros can be difficult to read
    > and maintain. But I do like how the compiler has an opportunity to remove
    > large parts of the code by switching a compiler flag.


    inline functions were largely created for the explicit purpose of
    eliminating macros.

    #define DO_STUFF doThis(); doThat();

    and

    inline void doStuff()
    {
    doThis();
    doThat();
    }

    should produce *exactly* the same output instructions under most
    circumstances (of course, the compiler is free to ignore the inline
    suggestion, and most do under certain circumstances). that's what they
    were created for.

    you want the power to be able to effectively turn that function off in
    certain compile-time conditions (eg, removing it in a release build)? no
    problem:

    inline void doStuff()
    {
    #ifdef DEBUG
    doThis();
    doThat();
    #endif
    }

    that will be a no-op on any compiler worth its salt if DEBUG is not
    defined. need a parameter? piece of cake:

    inline void doStuff(int param)
    {
    doThis(param);
    doThat(param);
    }

    just try that with macros:

    #define STUFF(x) doThis(x); doThat(x);
    STUFF(++i); // uh oh!

    also, what if you need a dummy/default variable for the call?

    inline void doStuff()
    {
    int temp;
    doThis(&temp);
    doThat(temp);
    }

    works with the macro? well...

    #define STUFF int temp; doThis(&temp); doThat(temp);

    void foo()
    {
    STUFF
    // some code
    STUFF // bang!
    }

    incidently:

    class MyUtils
    {
    public:
    static void doStuff() // implicit inline
    {
    doThis();
    doThat();
    }
    };

    would work, and may be valid in certain instances. i was involved in a
    lengthy debate about the merit of such a design pattern a while back. no
    real conclusion was reached, but i believe that 99% of the time this
    method is unnecessary and convoluted, and it's even occasionally
    dangerous. however, you're the programmer, do what you will.

    > I'm just interested in learning different techniques of performing the same
    > task, just to improve my toolbox :)


    bien sur. macros do have their place. and all the problems i presented
    above with the macros *could* be fixed. but seriously, how can you think
    inline funcitons are "too complicated" when you have to take so much
    care with them? use them only when direct text substitution is desired.
    _never_ use the preprocessor in place of c++ language constructs.

    as far as i can think right now, inline functions (and inlined static
    public class members of course) are about the only way to do what you
    want. macros *can* do it, if you're careful, but are most definitely not
    the best way to do it.

    of course, regular non-inlined functions could do the same thing,
    although possibly with additional overhead. i say this because often in
    the rush to optimize, rationality goes out the window. after all, you're
    already paying for the overhead *twice* with doThis() and doThat(). if
    either function takes any practical length of time, the overhead in
    calling doStuff() is pretty much marginalized.

    also, an optimizing compiler would probably realize that setting up the
    stack frame in doStuff is unnecessary, so the entire cost of the
    function (not counting doThis() and doThat(), of course) comes down to
    two jump instructions. that's two jump instructions, likely a call and a
    ret on x86's, and possibly even less in special cases. is that too
    expensive?

    and that's assuming the compiler doesn't inline it anyway. stay away
    from macro crap. trust your compiler... but use your profiler.

    mark
     
    Mark A. Gibbs, Jul 3, 2004
    #8
  9. "Mark A. Gibbs" <_x> wrote in message
    news:aqzFc.3242$...
    >
    > just use this.
    >
    > >>>namespace MyUtils
    > >>>{
    > >>> inline void doStuff()
    > >>> {
    > >>> doThis();
    > >>> doThat();
    > >>> }
    > >>>}
    > >>
    > >>That works, and most C++ purists would recommend it,
    > >>but I think it sucks. Too complicated. KISS.
    > >>Use the macro instead.

    >
    > this is probably the most bizarre thing i've read in a while. it works,
    > huh?:
    >
    > for (int i = 0; i < 10; ++i)
    > STUFF
    >
    > vs.
    >
    > for (int i = 0; i < 10; ++i)
    > doStuff();
    >
    > "kiss" that.
    >
    > > But macros can be difficult to follow too. This example is very

    simplistic,
    > > but for example logging macros and testing macros can be difficult to

    read
    > > and maintain. But I do like how the compiler has an opportunity to

    remove
    > > large parts of the code by switching a compiler flag.

    >
    > inline functions were largely created for the explicit purpose of
    > eliminating macros.
    >
    > #define DO_STUFF doThis(); doThat();
    >
    > and
    >
    > inline void doStuff()
    > {
    > doThis();
    > doThat();
    > }
    >
    > should produce *exactly* the same output instructions under most
    > circumstances (of course, the compiler is free to ignore the inline
    > suggestion, and most do under certain circumstances). that's what they
    > were created for.
    >
    > you want the power to be able to effectively turn that function off in
    > certain compile-time conditions (eg, removing it in a release build)? no
    > problem:
    >
    > inline void doStuff()
    > {
    > #ifdef DEBUG
    > doThis();
    > doThat();
    > #endif
    > }
    >
    > that will be a no-op on any compiler worth its salt if DEBUG is not
    > defined. need a parameter? piece of cake:
    >
    > inline void doStuff(int param)
    > {
    > doThis(param);
    > doThat(param);
    > }
    >
    > just try that with macros:
    >
    > #define STUFF(x) doThis(x); doThat(x);
    > STUFF(++i); // uh oh!
    >
    > also, what if you need a dummy/default variable for the call?
    >
    > inline void doStuff()
    > {
    > int temp;
    > doThis(&temp);
    > doThat(temp);
    > }
    >
    > works with the macro? well...
    >
    > #define STUFF int temp; doThis(&temp); doThat(temp);
    >
    > void foo()
    > {
    > STUFF
    > // some code
    > STUFF // bang!
    > }
    >
    > incidently:
    >
    > class MyUtils
    > {
    > public:
    > static void doStuff() // implicit inline
    > {
    > doThis();
    > doThat();
    > }
    > };
    >
    > would work, and may be valid in certain instances. i was involved in a
    > lengthy debate about the merit of such a design pattern a while back. no
    > real conclusion was reached, but i believe that 99% of the time this
    > method is unnecessary and convoluted, and it's even occasionally
    > dangerous. however, you're the programmer, do what you will.
    >
    > > I'm just interested in learning different techniques of performing the

    same
    > > task, just to improve my toolbox :)

    >
    > bien sur. macros do have their place. and all the problems i presented
    > above with the macros *could* be fixed. but seriously, how can you think
    > inline funcitons are "too complicated" when you have to take so much
    > care with them? use them only when direct text substitution is desired.
    > _never_ use the preprocessor in place of c++ language constructs.
    >
    > as far as i can think right now, inline functions (and inlined static
    > public class members of course) are about the only way to do what you
    > want. macros *can* do it, if you're careful, but are most definitely not
    > the best way to do it.
    >
    > of course, regular non-inlined functions could do the same thing,
    > although possibly with additional overhead. i say this because often in
    > the rush to optimize, rationality goes out the window. after all, you're
    > already paying for the overhead *twice* with doThis() and doThat(). if
    > either function takes any practical length of time, the overhead in
    > calling doStuff() is pretty much marginalized.
    >
    > also, an optimizing compiler would probably realize that setting up the
    > stack frame in doStuff is unnecessary, so the entire cost of the
    > function (not counting doThis() and doThat(), of course) comes down to
    > two jump instructions. that's two jump instructions, likely a call and a
    > ret on x86's, and possibly even less in special cases. is that too
    > expensive?
    >
    > and that's assuming the compiler doesn't inline it anyway. stay away
    > from macro crap. trust your compiler... but use your profiler.
    >
    > mark
    >


    Very enlightening post. I think that you might have mixed up who thought
    what about macros and inline functions, but it really doesn't matter.
    This was exactly the info about alternatives to macros I was looking for. :)
    Thanks a lot!

    /Carl
     
    Carl Ribbegaardh, Jul 3, 2004
    #9
  10. Carl Ribbegaardh wrote:

    > Very enlightening post. I think that you might have mixed up who thought
    > what about macros and inline functions, but it really doesn't matter.
    > This was exactly the info about alternatives to macros I was looking for. :)


    thank you, and don't worry, i was aware i was replying two steps removed
    when i was harping about the dangers of macros. sorry if i gave the
    impression otherwise.

    mark
     
    Mark A. Gibbs, Jul 3, 2004
    #10
  11. "Mark A. Gibbs" <_x> wrote:

    > just use this.
    >
    > >>>namespace MyUtils
    > >>>{
    > >>> inline void doStuff()
    > >>> {
    > >>> doThis();
    > >>> doThat();
    > >>> }
    > >>>}
    > >>
    > >>That works, and most C++ purists would recommend it,
    > >>but I think it sucks. Too complicated. KISS.
    > >>Use the macro instead.

    >
    > this is probably the most bizarre thing i've read in a while.


    Your reading must have been tame lately. :) Try Anne Rice.

    > it works, huh?:
    >
    > for (int i = 0; i < 10; ++i)
    > STUFF
    >
    > vs.
    >
    > for (int i = 0; i < 10; ++i)
    > doStuff();
    >
    > "kiss" that.


    Well, that's technically correct, but you're losing
    style points for no braces.

    If you really needed to use such a macro in a
    braceless loop like that, it COULD be done, though;
    just make a slight correction to the macro definition:

    #define DO_STUFF {doThis(); doThat();}

    Then this will work:

    for (int i = 0; i < 10; ++i)
    DO_STUFF

    > ... inline functions were largely created for the
    > explicit purpose of eliminating macros ...


    Well, for giving programmers an option that will be
    better than macros in many cases, at least.
    But I wouldn't say "eliminate". Note that the C and
    C++ standards committes have not removed macros from
    the languages, nor do I think that'll happen.

    I agree inline functions are better than macros in
    most cases; but if I want to simply paste-in a block
    of code in several (or many) places in a program,
    I'll sometimes use a macro:

    #define PASTE_HUGE_CODE_BLOCK_HERE \
    first line of code\
    second line of code\
    third line of code\
    (and so on, for many more lines)\
    last line of code

    #define PASTE_TINY_CODE_BLOCK_HERE b=7;

    int func1(double d)
    {
    ...
    PASTE_HUGE_CODE_BLOCK_HERE
    ...
    }

    float func2(int a, char b)
    {
    ...
    #ifdef FLAG_17
    PASTE_HUGE_CODE_BLOCK_HERE
    #else
    PASTE_TINY_CODE_BLOCK_HERE
    #endif
    ...
    }


    It's really just a matter of using the preprocessor
    as an automated compile-time text editor. As long as
    one remembers that macros are not functions, but just
    cut-n-pastes, the concept works.


    --
    Cheers,
    Robbie Hatley
    Tustin, CA, USA
    email: lonewolfintj at pacbell dot net
    web: home dot pacbell dot net slant earnur slant
     
    Robbie Hatley, Jul 4, 2004
    #11
  12. * Rolf Magnus:
    >
    > #define DO_STUFF do { doThis(); doThat(); } while(false)


    Unfortunately that may cause a warning with too "helpful" compilers
    such as Visual C++.

    Try instead

    #define DO_STUFF for(;;){ doThis; doThat(); break; }

    --
    A: Because it messes up the order in which people normally read text.
    Q: Why is it such a bad thing?
    A: Top-posting.
    Q: What is the most annoying thing on usenet and in e-mail?
     
    Alf P. Steinbach, Jul 4, 2004
    #12
  13. Carl Ribbegaardh

    Rolf Magnus Guest

    "Robbie Hatley" <lonewolfintj at pacbell dot net> wrote:

    >> it works, huh?:
    >>
    >> for (int i = 0; i < 10; ++i)
    >> STUFF
    >>
    >> vs.
    >>
    >> for (int i = 0; i < 10; ++i)
    >> doStuff();
    >>
    >> "kiss" that.

    >
    > Well, that's technically correct, but you're losing
    > style points for no braces.
    >
    > If you really needed to use such a macro in a
    > braceless loop like that, it COULD be done, though;
    > just make a slight correction to the macro definition:
    >
    > #define DO_STUFF {doThis(); doThat();}
    >
    > Then this will work:
    >
    > for (int i = 0; i < 10; ++i)
    > DO_STUFF



    If at all, I'd write the macro as:

    #define DO_STUFF do { doThis(); doThat(); } while(false)

    so that it can be used like a normal function in most cases. But I see
    no benefit over an inline function, which would be simpler.

    >> ... inline functions were largely created for the
    >> explicit purpose of eliminating macros ...

    >
    > Well, for giving programmers an option that will be
    > better than macros in many cases, at least.
    > But I wouldn't say "eliminate". Note that the C and
    > C++ standards committes have not removed macros from
    > the languages, nor do I think that'll happen.


    Of course not. It would make huge amounts of legacy code useless.
    However, that doesn't mean that you should still use macros where an
    inline function could be used.

    > I agree inline functions are better than macros in
    > most cases; but if I want to simply paste-in a block
    > of code in several (or many) places in a program,
    > I'll sometimes use a macro:
    >
    > #define PASTE_HUGE_CODE_BLOCK_HERE \
    > first line of code\
    > second line of code\
    > third line of code\
    > (and so on, for many more lines)\
    > last line of code


    I fail to see why you consider this to be more simple than:

    inline void paste_huge_code_block_here()
    {
    first line of code
    second line of code
    third line of code
    (and so on, for many more lines)
    last line of code
    }

    > #define PASTE_TINY_CODE_BLOCK_HERE b=7;
    >
    > int func1(double d)
    > {
    > ...
    > PASTE_HUGE_CODE_BLOCK_HERE
    > ...
    > }
    >
    > float func2(int a, char b)
    > {
    > ...
    > #ifdef FLAG_17
    > PASTE_HUGE_CODE_BLOCK_HERE
    > #else
    > PASTE_TINY_CODE_BLOCK_HERE
    > #endif
    > ...
    > }
    >
    >
    > It's really just a matter of using the preprocessor
    > as an automated compile-time text editor. As long as
    > one remembers that macros are not functions, but just
    > cut-n-pastes, the concept works.


    That's the point. You have to remember, and take are. You don't have to
    do that with inline functions.
     
    Rolf Magnus, Jul 4, 2004
    #13
  14. Carl Ribbegaardh

    JKop Guest


    > #define DO_STUFF do { doThis(); doThat(); } while(false)



    How would that be in any way different to:


    #define DO_STUFF { doThis(); doThat(); }


    ?


    -JKop
     
    JKop, Jul 4, 2004
    #14
  15. Carl Ribbegaardh

    Rolf Magnus Guest

    JKop wrote:

    >
    >> #define DO_STUFF do { doThis(); doThat(); } while(false)


    I meant:

    #define DO_STUFF() do { doThis(); doThat(); } while(false)

    >
    >
    > How would that be in any way different to:
    >
    >
    > #define DO_STUFF { doThis(); doThat(); }
    >
    >
    > ?


    if (x) DO_STUFF(); else whatever();

    This won't compile with the latter one.
     
    Rolf Magnus, Jul 4, 2004
    #15
  16. Carl Ribbegaardh

    Rolf Magnus Guest

    Alf P. Steinbach wrote:

    > * Rolf Magnus:
    >>
    >> #define DO_STUFF do { doThis(); doThat(); } while(false)

    >
    > Unfortunately that may cause a warning with too "helpful" compilers
    > such as Visual C++.
    >
    > Try instead
    >
    > #define DO_STUFF for(;;){ doThis; doThat(); break; }


    Hmm, what would you gain with that for loop?
     
    Rolf Magnus, Jul 4, 2004
    #16
  17. * Rolf Magnus:
    > Alf P. Steinbach wrote:
    >
    > > * Rolf Magnus:
    > >>
    > >> #define DO_STUFF do { doThis(); doThat(); } while(false)

    > >
    > > Unfortunately that may cause a warning with too "helpful" compilers
    > > such as Visual C++.
    > >
    > > Try instead
    > >
    > > #define DO_STUFF for(;;){ doThis; doThat(); break; }

    >
    > Hmm, what would you gain with that for loop?


    See above.

    And right, as you mention elsewhere, there should be empty arg list for
    the macro.

    --
    A: Because it messes up the order in which people normally read text.
    Q: Why is it such a bad thing?
    A: Top-posting.
    Q: What is the most annoying thing on usenet and in e-mail?
     
    Alf P. Steinbach, Jul 4, 2004
    #17
  18. Alf P. Steinbach wrote in news: in
    comp.lang.c++:

    > * Rolf Magnus:
    >>
    >> #define DO_STUFF do { doThis(); doThat(); } while(false)

    >
    > Unfortunately that may cause a warning with too "helpful" compilers
    > such as Visual C++.


    Yep VC++ has some distinctly un-useful warnings on by default.
    I turn them off.

    >
    > Try instead
    >
    > #define DO_STUFF for(;;){ doThis; doThat(); break; }
    >


    if DO_STUFF;
    else doThat();

    The advantage of the "do .. while(false)" is it allows the
    trailing semicolon, your version might as well be:

    #define DO_STUFF { doThis; doThat(); }

    Though in this case, I'd prefer:

    #define DO_STUFF() ( doThis(), doThat() )

    Rob.
    --
    http://www.victim-prime.dsl.pipex.com/
     
    Rob Williscroft, Jul 4, 2004
    #18
  19. * Rob Williscroft:
    > Alf P. Steinbach wrote in news: in
    > comp.lang.c++:
    >
    > > * Rolf Magnus:
    > >>
    > >> #define DO_STUFF do { doThis(); doThat(); } while(false)

    > >
    > > Unfortunately that may cause a warning with too "helpful" compilers
    > > such as Visual C++.

    >
    > Yep VC++ has some distinctly un-useful warnings on by default.
    > I turn them off.
    >
    > >
    > > Try instead
    > >
    > > #define DO_STUFF for(;;){ doThis; doThat(); break; }
    > >

    >
    > if DO_STUFF;
    > else doThat();
    >
    > The advantage of the "do .. while(false)" is it allows the
    > trailing semicolon, your version might as well be:
    >
    > #define DO_STUFF { doThis; doThat(); }
    >
    > Though in this case, I'd prefer:
    >
    > #define DO_STUFF() ( doThis(), doThat() )


    Right, sorry.

    I've always used the do-while version, for exactly that reason,
    and even preaching it to others.

    Smartass, Alf. Smartass.

    --
    A: Because it messes up the order in which people normally read text.
    Q: Why is it such a bad thing?
    A: Top-posting.
    Q: What is the most annoying thing on usenet and in e-mail?
     
    Alf P. Steinbach, Jul 4, 2004
    #19
  20. Carl Ribbegaardh

    Rolf Magnus Guest

    Alf P. Steinbach wrote:

    > * Rolf Magnus:
    >> Alf P. Steinbach wrote:
    >>
    >> > * Rolf Magnus:
    >> >>
    >> >> #define DO_STUFF do { doThis(); doThat(); } while(false)
    >> >
    >> > Unfortunately that may cause a warning with too "helpful" compilers
    >> > such as Visual C++.
    >> >
    >> > Try instead
    >> >
    >> > #define DO_STUFF for(;;){ doThis; doThat(); break; }

    >>
    >> Hmm, what would you gain with that for loop?

    >
    > See above.


    No, I mean what you gain compared to just:

    #define DO_STUFF() { doThis(); doThat(); }
     
    Rolf Magnus, Jul 4, 2004
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Robert V. Hanson
    Replies:
    2
    Views:
    670
    Yan-Hong Huang[MSFT]
    Jul 3, 2003
  2. Don Pedro
    Replies:
    0
    Views:
    466
    Don Pedro
    Jul 3, 2003
  3. theotyflos
    Replies:
    3
    Views:
    474
    Thomas Matthews
    Feb 19, 2004
  4. robin liu
    Replies:
    3
    Views:
    824
    Robin Liu
    Apr 21, 2006
  5. Brian Takita

    #define _ and #define __

    Brian Takita, Jan 23, 2006, in forum: Ruby
    Replies:
    0
    Views:
    467
    Brian Takita
    Jan 23, 2006
Loading...

Share This Page