Richard said:
No, it has to do with how C++ IDEs and other development tools integrate
into the environment provided by your chosen OS. That has nothing to do
with the language itself.
This is not the case. The problems I am describing are not platform
specific. I can emulate a DOS shell under Linux, and I can run a posix
compliant shell under NT(AKA XP). Almost all tools I use are platform
independent. A person who does not have a reason to deal with the issues
related to using different tools at different times to work on the same
code base will probably not appreciate the nature of my concerns. If a
person has never studied the problem of parsing C++ source code to extract
useful information to provide to the programmer at edit time, he will
probably not appreciate the difficulties introduced by the use of the
preprocessor. If I were to restrict myself to using only one set of tools
in a clearly defined environment such as NT user space where I could, more
or less, predict all the variables, much of the problems I am describing
would be non-issues. That is not the spirit in which C++ was created, and
it is not good for the longterm health of the computing field.
Nonetheless, some of this goes beyond using multiple tools. It is utterly
absurd to have a langue support features that cause a compiler to detect
errors in code located in "header files" the programmer did not write, and
which contain no errors, because there is a minor syntax error in code the
programmer did write. But this happens with C++.
I understand the advantage the preprocessor provides to C++ programmers. It
allows for the crossing of the boundary between the language and the
observer of the language. This is a form of selfreferential recursion that
we might call selfawareness, or introspection. Stringification demonstrates
this very well. If I want my program to contain both the product of
compiling a function definition, and the human readable information
contained in the function definition, I have to have a way to access that
human readable information at runtime. Stringizing such information with a
Macro is a way to generate both the source and a characters representation
of the source to be included in the program at runtime.
With some languages such as Mathematica, Lisp, Java, ECMAScript, C#(?), that
is simply part of the way the language works. With the interpreted
languages, it is rather straight forward. The source code *is* the
executable. With compiled languages, it takes more intentional thought to
support such a feature.
I understand that C++ would incur costs in both space and time if such
introspection were required of all executable code. Introducing support
for it into the core language might add excessive complexity to an already
dauntingly complex specification.
All that being said, I believe much use of the preprocessor to generate
cookiecutter code is a way for the programmer to avoid correctly solving
the underlying programming problem. Virtually every use of the
preprocessor that I have seen that could not be replaced with a native C++
construct has to do with storing information about the source code to be
available at runtime.
--
"If our hypothesis is about anything and not about some one or more
particular things, then our deductions constitute mathematics. Thus
mathematics may be defined as the subject in which we never know what we
are talking about, nor whether what we are saying is true." - Bertrand
Russell