Ritchie
declaration of a variable resembles its usage in an expression whose type is the one named at the
head of the declaration.
The scheme of type composition adopted by C owes considerable debt to Algol 68,
although it did not, perhaps, emerge in a form that Algol’s adherents would approve of. The central
notion I captured from Algol was a type structure based on atomic types (including structures),
composed into arrays, pointers (references), and functions (procedures). Algol 68’s concept
of unions and casts also had an influence that appeared later.
After creating the type system, the associated syntax, and the compiler for the new language,
I felt that it deserved a new name; NB seemed insufficiently distinctive. I decided to follow
the singleletter
style and called it C, leaving open the question whether the name represented
a progression through the alphabet or through the letters in BCPL.
Neonatal C
Rapid changes continued after the language had been named, for example the introduction
of the
within
languages place a special interpretation on the
they operate bitwise, but in the B statement
&& and || operators. In BCPL and B, the evaluation of expressions depends on context:if and other conditional statements that compare an expression’s value with zero, theseand (&) and or (|) operators. In ordinary contexts,if (e1 & e2) ...
the compiler must evaluate
evaluate
elaborate
the statement dependent on the
within
semantics of the Boolean operators in such ‘truthvalue’
context seemed desirable, but the overloading of the operators was difficult to explain and use.
At the suggestion of Alan Snyder, I introduced the
more explicit.
Their tardy introduction explains an infelicity of C’s precedence rules. In B one writes
e1 and if it is nonzero,e2, and if it too is nonzero,if. The requirement descends recursively on & and | operatorse1 and e2. The shortcircuit&& and || operators to make the mechanismif (a==b & c) ...
to check whether
in such a conditional expression it is better that
a equals b and c is nonzero;&have lower precedence than
a statement; to make the conversion less painful, we decided to keep the precedence of the
==. In converting from B to C, one wants to replace & by && in such&operator the same relative to
seems that it would have been preferable to move the relative precedences of
thereby simplify a common C idiom: to test a masked value against another value, one must write
==, and merely split the precedence of && slightly from &. Today, it& and ==, andif ((a&mask) == b) ...
where the inner parentheses are required but easily forgotten.
Many other changes occurred around 19723,
but the most important was the introduction
of the preprocessor, partly at the urging of Alan Snyder [Snyder 74], but also in recognition of the
utility of the the fileinclusion
mechanisms available in BCPL and PL/I. Its original version was
exceedingly simple, and provided only included files and simple string replacements:
#includeand
and then by John Reiser, to incorporate macros with arguments and conditional compilation. The
preprocessor was originally considered an optional adjunct to the language itself. Indeed, for
some years, it was not even invoked unless the source program contained a special signal at its
beginning. This attitude persisted, and explains both the incomplete integration of the syntax of
the preprocessor with the rest of the language and the imprecision of its description in early reference
manuals.#define of parameterless macros. Soon thereafter, it was extended, mostly by Mike Lesk
No comments:
Post a Comment
THE WORLD NEW TECHNOLOGY