Another newbie (gah) question :-)

Started by
13 comments, last by Llamasoft.net 24 years ago
To Hell with cout. I''ve been programming for a long damn time and I still can''t figure it out.

How, for instance, would you do this with cout?

sprintf(buf, "%-30s''s total is %6.2f\n",
(winner)?you->name : me->name,
GetValue(me));

-?
Advertisement
quote:Original post by Buster
How, for instance, would you do this with cout?

sprintf(buf, "%-30s''s total is %6.2f\n",
(winner)?you->name : me->name,
GetValue(me));

Let''s just say that I could have shown you if I had figured out what your code is doing
Ever heard of stl and stringstreams?
A polar bear is a rectangular bear after a coordinate transform.
Zipster is partially correct -- #define''s can be used to create macros (as he showed), but as others said, it also is the old C way of doing constants. So basically, if you''re using C++, use const instead (unless you want to make a macro). By the way, macros do have certain advantages over functions, but I don''t feel like going into that right now

If you code it, they will come...

Commander M
http://commanderm.8m.com
cmndrm@commanderm.8m.com
Macros do replace the code with a hard coded constant, but it is not type-safe. It is a variable. The const keyword only reflects that. =, +, etc. are binary operators. That is, they require two variables. You can't add int + 5, you must add an int plus an int. You also can't do anything with 5, unless it is in memory, or a VARIABLE. What the compiler does is to make a temporary const int, and pass it to the + operator.

const just shows you what is going on "behind the scenes" and allows you to control it better.

Now, back to original question, which was "Exactly *WHY* are '#define's so good?" The answer to that is that people don't know what #defines really do and think that they are some kind of cure-all or performance helper. Anyone who thinks the compiler cannot optimize these two statements in any way it wishes does not know what they are talking about:


const int TileWidth = 32; // 32 pixels X 32 pixels
const int TileHeight = 32;

#define TILE_WIDTH 32
#define TILE_HEIGHT 32

void main()
{
int Size1 = TileWidth * TileHeight;
int Size2 = TILE_WIDTH * TILE_HEIGHT;
}



Also, you should always use inline functions instead of #define-ing macros. Doing so allows the compiler (and its profiler) to determine whether to emphasize speed or memory size. In short, inline functions can do everything macro "functions" can, plus allow the compiler much more flexibility in optimization.

They use CAPITAL_LETTERS to remind themselves that they are using macros and not real constants.

Macros should only be used for code that MUST be substituted BEFORE compile time. Zipster's and Domini's examples are prime candidates for inline functions, because they don't do any special pre-processing. Those examples were just "functions." Also, for constants, you get no benefit from using macros -- you can actually hinder performance.

You can use macros to create something like this, however:


#define DECLARE_MESSAGE_MAP /
virtual void OnMessage();

#define BEGIN_MESSAGE_MAP( class ) /
void class::OnMessage() /
{ /
switch( m_nMsg ) /
{

#define ON_MESSAGE( ID, handler ) /
case ID: /
handler(); /
break;

#define END_MESSAGE_MAP( baseclass ) /
default: /
baseclass::OnMessage(); /
break; /
} /
}



Then, when you want to build a message-handler, you do this:


BEGIN_MESSAGE_MAP( Dialog )
{
ON_MESSAGE(WM_COMMAND, OnCommand)
ON_MESSAGE(WM_PAINT, OnPaint)
ON_MESSAGE(WM_CLOSE, OnClose)
}
END_MESSAGE_MAP( Window )



And that turns into this before compile-time:


void Dialog::OnMessage()
{
switch( m_nMsg )
{
case WM_COMMAND:
OnCommand();
break;

case WM_PAINT:
OnPaint();
break;

case WM_CLOSE:
OnClose();
break;

default:
Window::OnMessage();
break;
}
}



So, we built a function from parts using macros. Not too bad, but you might be able to do it better another way. I haven't looked into this situation much.


quote: Original post by Armitage

And the difference between const in c and const in c++ is that the const in c means "this cannot be changed" whereas the const in c++ defines a new type, eg "const int" instead of a constant "int".


You mean: "C++ uses stricter type-checking." Right? Because the only real difference is in the syntax checking...not at run-time.



- null_pointer
Sabre Multimedia

Edited by - null_pointer on 5/5/00 8:16:02 AM
The nullster is right

If the compiler sees "const int variable = 12" it knows that will not change in the code and can treat it exactly the same way as it would treat "#define variable 12". (Of course, stick the keyword ''volatile'' in there and it all changes. But then you couldn''t really use a #define to declare a volatile variable anyway.)

Because the compiler knows ''variable'' is an int, it can warn you if you try to pass it to a function that takes a char, for instance. And it''s always better to have the compiler catch your errors than for you to stare at it for an hour thinking "why isn''t this working"...

And using inline functions instead of macro-style functions avoids this type of error:
#define AdditionMacro (x) + (x)int u = 1;int v = AdditionMacro(u++)cout << v; // displays 3, when you expect 2. Probably cout << u; // as above 

As with a #define, the ++ operator will be expanded twice and used twice.

I very rarely use #define in my code. One place is where I need to substitute in a block of code like this:

if (x) == (y) { DoSomething(); continue; }

This always goes within a while loop, and although I could inline it, the continue could no longer be there and therefore it slows my outer loop down (I know, as I have tried it).

One other place is where I am using the same function signature over and over again, so I use #define to reduce the amount of typing needed, and hence mistakes:

#define SOME_FUNC int SomeFunction(Variable* x, OtherVariable& y, ThirdVariableList zl, List::iterator li)

I thought I could do this with a typedef, but it didn''t seem to work.

But the above two cases are the only times I''ve really had to use #define for anything.

This topic is closed to new replies.

Advertisement