Re: I don't have to tell you...
"Howard Beale"
For example, I remember running into the oh-so-popular "OnInitDialog"
bug. For anyone who hasn't seen it before, it's a textbook example of
the behavior we're talking about. The function OnInitDialog() is a
method in the MFC's CDialog class. You're expected to override the
function and initialize your own dialog's controls there. And just
about everyone runs into this weird assertion that looks something like
this:
ASSERT(::IsWindow(m_hWnd))
I mean seriously, EVERY SINGLE newbie EVER hits this bug on their first
foray into MFC. The reason for the assertion is that you've done this:
Ah, more lies. I was a newbie, I used MFC (a lot), never had a problem
wioth that.
Maybe I read the MFC dox? Maybe I used it as intended by creators: click the
message to create the handler -- then put my code where it said
//TODO: insert your code here
? That was certainly *after* the call of the original?
BOOL MyDialogClass::OnInitDialog()
{
my_control_1.do_something();
my_contril_2.set_something("string");
return CDialog::OnInitDialog();
}
Quite obviously your control objects are bound wo UI objects in that last
call. MFC uses two-phase setup for many things.
Guess saying
CFile file;
file.Read(....);
is as surprizing -- who woud think to Open the frelling file? By either
calling Open, or using the ctor version that does that.
Or newbie is defined as 'I never RTFM, and have the right to troll if
something will not work as I just hack around random code'?
You need to call the base class version *before* doing anything with the
controls.
More precisely, you have to Attach() or use some similar 2nd phase init call
on your controls, directly or indirectly. And in general, have a clue about
both windows and the framework to do anything sensible. If so, work can be
done -- and having the bonus of hitting sensible asserts in *debug* builds
is good, when you do some clear nonsense.
Dereference a NULL pointer or sending message to a unknown window qualifies
fine.
But you're free to do other things (setup data structures, or
whatever) before. That's the nature of the beast. You need to
understand what the base class does before you go deriving your own
class from it. Constructors and destructors don't need to be any
different.
And they aren't. Actually nothing fobids an implementation to add turn the
language into a kindergarten, and generate code with asserts on a whim...
Or generate warnings like that.
The mentioned VC does it too -- using this in the member init list triggers
a warning. One that would make sense to those trying to use it right away,
and annoying to those who just store it for later. Same could be done for
any other use case, maybe it would make the build time explode, or annoy
more users who actuallt did RTFM and know what they do -- or just use other
more straightforward means to detect traps as testing. TANSTAAFL. Decision
to just leave it can be is as reasonable, or more so.
There are open source compilers, you can do it yourself, or convince other
developers how cool your way would be -- real life compilers come with cool
extensions.
Sure actual work is hard, while whining is cheap.