Static Wikipedia February 2008 (no images)

aa - ab - af - ak - als - am - an - ang - ar - arc - as - ast - av - ay - az - ba - bar - bat_smg - bcl - be - be_x_old - bg - bh - bi - bm - bn - bo - bpy - br - bs - bug - bxr - ca - cbk_zam - cdo - ce - ceb - ch - cho - chr - chy - co - cr - crh - cs - csb - cu - cv - cy - da - de - diq - dsb - dv - dz - ee - el - eml - en - eo - es - et - eu - ext - fa - ff - fi - fiu_vro - fj - fo - fr - frp - fur - fy - ga - gan - gd - gl - glk - gn - got - gu - gv - ha - hak - haw - he - hi - hif - ho - hr - hsb - ht - hu - hy - hz - ia - id - ie - ig - ii - ik - ilo - io - is - it - iu - ja - jbo - jv - ka - kaa - kab - kg - ki - kj - kk - kl - km - kn - ko - kr - ks - ksh - ku - kv - kw - ky - la - lad - lb - lbe - lg - li - lij - lmo - ln - lo - lt - lv - map_bms - mdf - mg - mh - mi - mk - ml - mn - mo - mr - mt - mus - my - myv - mzn - na - nah - nap - nds - nds_nl - ne - new - ng - nl - nn - no - nov - nrm - nv - ny - oc - om - or - os - pa - pag - pam - pap - pdc - pi - pih - pl - pms - ps - pt - qu - quality - rm - rmy - rn - ro - roa_rup - roa_tara - ru - rw - sa - sah - sc - scn - sco - sd - se - sg - sh - si - simple - sk - sl - sm - sn - so - sr - srn - ss - st - stq - su - sv - sw - szl - ta - te - tet - tg - th - ti - tk - tl - tlh - tn - to - tpi - tr - ts - tt - tum - tw - ty - udm - ug - uk - ur - uz - ve - vec - vi - vls - vo - wa - war - wo - wuu - xal - xh - yi - yo - za - zea - zh - zh_classical - zh_min_nan - zh_yue - zu

Web Analytics
Cookie Policy Terms and Conditions Comparison of Pascal and C - Wikipedia, the free encyclopedia

Comparison of Pascal and C

From Wikipedia, the free encyclopedia

This article is part of
the Programming Language Comparison
series.
General Comparison
Basic Syntax
String Operations
String Functions

Evaluation strategy
List of "hello world" programs

Compatibility of C and C++
Comparison of C and Pascal
Comparison of C++ and Java
Comparison of C# and Java
Comparison of C# and Visual Basic .NET


Contents

[edit] Background

C and Pascal are often compared* to each other, sometimes heatedly, probably because the languages have similar times of origin, influences, and purposes, and so represent two philosophical approaches to a similar need. Both were used to design (and compile) their own compilers early in their lifetimes, and both were established and popular during the formative years of the microcomputer age.

Both C and Pascal are quite old languages. An original Pascal definition appeared in 1969 and a first compiler in 1970, the first version of C a few years later, around 1972. Both are arguably descendants of the ALGOL language series.

Algol introduced so called structured programming, where programs are constructed of single entry and single exit constructs such as if, while, for, case, and so on. Furthermore, only expression syntaxes were (more or less) systematically described before Algol, which defined the entire language syntax in terms of a recursive grammar (BNF). This tended to make the language more general and regular.

Pascal stems directly from AlgolW, while it shared some new ideas with Algol68. The C language is more indirectly related to Algol, originally through B, BCPL, and CPL, and later through Algol68 (struct, union etc) and also Pascal (enumerations, const, typedef, booleans). Important Pascal dialects (and later, standards) also incorporated characteristics from C, see further below.

The modern versions of the languages have become quite similar, especially types and data structuring possibilities, but also control structures and general layout are (very) roughly equivalent. The most important remaining differences concerns declaration syntax, expression evaluation, nested procedures, and modular programming (separate compilation).

* It would be less interesting to compare, say, C with Lisp, or Pascal versus Perl, as these languages are so clearly different and have very different aims.

[edit] Syntax

Both C and Pascal use semicolons between statements. In C they terminate every statement, while in Pascal they separate statements. In practice, there is little difference between these schemes. The bigger difference in on loops or function declaring, such as in C

if (...)
{
...
}

you must not put a ;, but in PASCAL

if ... then
begin
...
end ;

you must. On the other hand, if in C there's a single non-block statement before else, you must have a semicolon, as in

if (...)
  ...;
else
  ...;

while in Pascal, you may not put a semicolon here, as in

if ... then
  ...
else
  ...;

In C, comments are formed by /* comments */, and // line comments. In Pascal, there are (* comments *) and { comments }.

[edit] Identifiers

C and Pascal differ in their interpretation of upper and lower case. In Pascal case does not matter, in C it does. Thus MyLabel and mylabel are two different identifiers in C, but the same identifier in Pascal. This may cause problems if object files generated from the two languages are linked together.

In both languages, identifiers consists of letters, digits, and underscores ("_") with the rule that the first character may not be a digit. In C names that begin with "_" are sometimes used to differentiate special system identifiers. Certain Pascal systems use this convention as well.

[edit] Keywords

Both C and Pascal use keywords, or words reserved for use by the language itself. Examples are if, while, const, for and goto, which are keywords that happen to be common to both languages.

In Pascal, blocks begin and end with begin and end. C uses "{" and "}", respectively. In Pascal, a function definition starts with the keyword function and a type definition with type. In C, function definitions are determined by syntactical context while type definitions use the reserved word typedef.

In C, the basic built-in types are named with keywords (e.g. int, char) or combinations of keywords (e.g. unsigned char), while in Pascal the names of basic types are normal identifiers. On the other hand, Pascal uses the keyword array to declare arrays, while in C only punctuation is used for that purpose.

[edit] Implementation

The grammars of both languages are of a similar size. From an implementation perspective the main difference between the two language is that to parse C it is necessary to have access to a symbol table, while in Pascal there is no such requirement. For instance, in C, the following:

X * Y;

could be a declaration of Y to be an object whose type is pointer to X, or a statement-expression that multiplies X and Y.

[edit] Simple types

[edit] Integers

Pascal requires all variable and function declarations to explicitly specify their type. In traditional C, a type name may be omitted in most context and the default type int (which corresponds to integer in Pascal) is then implicitly assumed. However, this has been removed from the language as of the C99 standard.

C accommodates different sizes and signed and unsigned modes for integers by using modifiers such as long, short, signed, unsigned, etc. The exact meaning of the resulting integer type is machine-dependent, however, what can be guaranteed is:

  • long long int is no shorter than long int
  • long int is no shorter than int
  • int is no shorter than short int

Even char is actually a kind of integer that is no longer than short int, this integer nature of char (an eight-bit byte on most machines) is clearly illustrated by declarations such as

unsigned char uc = 255;  /* common limit */
signed char sc = −128;   /* common negative limit */

There has been some controversy as whether the char type should be regarded as signed or unsigned by default.

[edit] Subranges

In Pascal, a similar end is performed by declaring a subrange of integer (a compiler may then choose to allocate a smaller amount of storage for the declared variable):

type a = 1..100;
     b = -20..20;
     c = 0..100000;

This subrange feature (simply called a "range") is not supported by C.

A major, if subtle, difference between C and Pascal is how they promote integer operations. In Pascal, all operations on integers or integer subranges have the same effect, as if all of the operands were promoted to a full integer. In C, there are defined rules as to how to promote different types of integers, typically with the effect that the result of two integers will have a precision that is the greater of the operands'. This can make machine code generated from C simpler and more efficient on many processors. A highly optimizing Pascal compiler can reduce, but not eliminate, the effect of this under standard Pascal rules. A side effect of this Pascal feature is that many Pascal compilers extend the language to include special integer types and promotion rules.

Some early pre-Standard implementations of C formerly allowed integer and pointer types to be relatively freely intermixed.

[edit] Character types

In C the character type is char which, as mentioned above, is interchangeable with integer types in C. Expressions such as 'x'+1 are therefore perfectly legal, as are declarations such as int i='i'; and char c=74;

In Pascal, character types are distinct types, and are rarely used as general integers. A character (like most simple types) may be converted to an integer via the function ord. An integer may be converted into a character with the function chr.

[edit] Boolean types

In Pascal, boolean is an enumerated type. The possible values of boolean are false and true. For conversion to integer, ord is used:

i := ord(b);

There is no language special function for integer to boolean, however, the conversion is in practice simple:

b := i <> 0;

C has binary valued relational operators (<, >, ==, !=, <=, >=) which may be regarded as boolean in the sense that they always give results which are either zero or one. Prior to the 1999 version of the Standard C had no specific boolean type. As all tests (&&, ||, ?:, if, while, etc.) are performed by zero-checks, false is represented by zero, while true is represented by any other value.

[edit] Newer C-versions

The 1999 revision of the C Standard introduced the type _Bool which (like the operators and statements mentioned above) map all non-zero values onto 1, when assigned or converted to. _Bool typed variables may be operated on by the additive (+, ++, +=) and subtractive operators. Thus, "incrementing" a _Bool typed variable will set it to 1, while "decrementing" it will complement the stored value (0 becomes 1 and 1 becomes 0).

The values true and false are defined as macros whose bodies are 1 and 0 respectively.

[edit] Bitwise operations

The C programmer may sometimes use bitwise operators to perform boolean operations. Care needs to be taken because the semantics are different when operands make use of more than one bit to represent a value.

In Pascal dialects with bitwise operations (such as Borland), the relational operator symbols (and, or, etc) have bitwise semantics for operands which are integer typed, while retaining traditional boolean semantics for boolean operands (overloaded in popular terms). Thus, harder typing reduces the need for a plethora of operator symbols.

Pascal has another more abstract, high level method of dealing with bitwise data, sets. Sets allow the programmer to set, clear, intersect, and unite bitwise data values, rather than using direct bitwise operators. Example;

Pascal:  Status := Status + [StickyFlag];
         Status := Status - [StickyFlag];
         IF (StickyFlag IN Status) THEN ...
     c:  Status = Status | StickyFlag;
         Status = Status & (~StickyFlag);
         if (Status & StickyFlag) { ...

[edit] A note on implementation

During expression evaluation, and in both languages, a boolean value may be internally stored as a single bit, a single byte, a full machine word, a position in the generated code, or as a condition code in a status register, depending on machine, compiler, and situation; these factors are usually more important than the language compiled.

[edit] Floating point types

C offers a more sophisticated model of floating point types than Pascal, although few developers appreciate the subtle differences. In C, integers may be implicitly converted to floating point numbers, and vice versa. In Pascal, integers may be implicitly converted to real, but conversion of real to integer (where information may be lost) must be done via the functions trunc and round, which truncate or round off the fraction, respectively.

[edit] Enumeration types

Both C and Pascal include enumeration types. A Pascal example:

type
  color = (red, green, blue);
var
  a: color;

A C example:

enum color {
  RED, GREEN, BLUE
};
enum color a;

The behavior of the types in the two languages however is very different. In C, RED becomes just a synonym for 0, GREEN for 1, BLUE for 2, and nothing prevents a value outside this range to be assigned to the variable a. Furthermore, operations like a = a + 1; are strictly forbidden in Pascal.

[edit] Structured types

[edit] Array types

Both C and Pascal allow arrays of other complex types, including other arrays. However, there the similarity between the languages ends. C arrays are simply defined by a base type and the number of elements:

int a[SIZE];

and are always indexed from 0 up to SIZE-1 (i.e. modulo SIZE).

In Pascal, the range of indices is often specified by a subrange (as introduced under simple types above). The ten elements of

var a : array [0..9] of integer;

would be indexed by 0..9 (just as in C in this case). Array indices can be any ordinal type, however, not just ranges:

type
   color = (red, green, blue);       (* enumeration *)
   RGB = array [color] of 0..255;

var picture : array [1..640,1..480] of RGB

[edit] Arrays and pointers

In C expressions, an identifier representing an array is treated as a constant pointer to the first element of the array, thus, given the declarations int a[10] and int *p; the assignment p = a is valid and causes p and a to point to the same array. As the identifier a represents a constant address, a = p is not valid however.

While arrays in C are fixed, pointers to them are interchangeable. This flexibility allows C to manipulate any length array using the same code. It also leaves the programmer with the responsibility not to write outside the allocated array, as no checks are built in into the language itself.

In Pascal, arrays are a distinct type from pointers. This makes bounds checking for arrays possible from a compiler perspective. Practically all Pascal compilers support range checking as a compile option. The ability to both have array that change length at runtime, and be able to check them under language control, is often termed "dynamic arrays".

Pascal has a function similar to C's sizeof function, which is often used to obtain the size of a statically initialized array in C code. For instance in the following code, the terminating index for the loop automatically adjusts should the list of strings be changed.

static char *wordlist[] = {
   "print",   "out",   "the",  "text",   "message" };
static int listSize = (sizeof(wordlist)/sizeof(char *));
int i;

for (i=0; i<listSize; i++)
   puts(wordlist[i]);

The equivalent in Pascal:

 TYPE
   sarr=array[0..4] of string;
   Const wordlist:sarr = ('print','out','the','text','message');
 VAR
   i:integer;
 ...
   for i:=0 to sizeof(wordlist) DIV sizeof(string) do
     Writeln(wordlist[i]);

[edit] Strings

Neither C nor Pascal have more than rudimentary support for character strings, and both also (reasonably) consider strings to be a special case of the array. In both languages, it is the programmer's responsibility to determine the (runtime) length of a string stored in a character array.

C automatically terminates string literals with a trailing null-character as an end-of-string "sentinel":

char *p;
p = "the rain in Spain";     /* null-terminated */

Null-termination must be manually maintained for string variables stored in arrays (this is often partly handled by library routines). C does not have built in string or array assignment, so the string is not actually being transferred to p, but rather p is being made to point to the constant string in memory.

Pascal does have array assignment and string literals may be assigned to packed character arrays that has starting index 1, however, the length must match the type exactly:

type string = packed array [1..20] of char;
var s: string;
s := 'the rain in Spain  ';     (* actual copying *)

Pascal strings are conceptually of equal length and string literals must be padded out to force type equality (it is most common to pad strings with spaces on the right side, but this is purely a programmer convention). This, along with the general lack of dynamic string support, is considered to be a problem with the classic form of the language, however it must be noted that many modern Pascal implementations therefore have dynamic strings as a language extension.

[edit] Record types

Both C and Pascal can declare record types. In C, they are termed "structures".

struct a {
   int b;
   char c;
};
type a = record 
   b: integer;
   c: char
end;

In C, the exact bit length of a field can be specified:

struct a {
   int b:3;
   int c:1;
};

This feature may be available in Pascal by using the subrange construct (3 bits gives a range from 0 to 7). It depends on whether the compiler used packs subranges into the smallest available storage:

type a = record
   b: 0..7;
   c: 0..1
end;

Both C and Pascal support records which can include different fields overlapping each other:

union a {
   int a;
   float b;
};
type a = record
   case boolean of
      false: (a: integer);
      true:  (b: real)
end;

Both language processors are free to allocate only as much space for these records as needed to contain the largest type in the union/record.

The biggest difference between C and Pascal is that Pascal supports the explicit use of a "tagfield" for the language processor to determine if the valid component of the variant record is being accessed:

type a = record
   case q: boolean of
      false: (a: integer);
      true:  (b: real)
end;

In this case, the tagfield q must be set to the right state to access the proper parts of the record.

C, in its original version, could not assign objects having a struct type or pass them to functions (Pascal can). Structure assignment was however, widely implemented in 'C' compilers by the mid 1980s. Passing structures, and not just pointers to structures, was later implemented by many compilers. This capability was added to C in C99.

[edit] Pointers

In C, pointers can be made to point at most program entities, including objects or functions:

int a;
int *b;
int (*compare)(int c, int d);
int  MyCompare( int c, int d);

b = &a;
compare = &MyCompare;

In C, since arrays and pointers have a close equivalence, the following are the same:

a = b[5];
a = *(b+5);

Thus, pointers are often used in C as just another method to access arrays.

To create dynamic data, the library functions "malloc" and "free" are used to obtain and release dynamic blocks of data. Thus, dynamic memory allocation is not built into the language processor. This is especially valuable when C is being used in operating system kernels or embedded targets as these things are very platform (not just architecture) specific and would require changing the C compiler for each platform (or operating system) that it would be used on.

Pascal doesn't have the same kind of pointers like C, but it does have an indirection tool that covers the most common use of C pointers. Each pointer is bound to a single dynamic data item, and can only be moved by assignment:

type a = ^integer;

var b, c: a;

new(b);
c := b;

In classic ANSI Pascal, pointers can never point to program objects such as local or global variables. This appears to make Pascal more type safe than C, but Pascal can still have invalid pointer references in several ways. For example, a pointer can be referenced when uninitialized, or it would be referenced after it is disposed, etc.

In modern Pascal (BP, Delphi, GNU Pascal, FreePascal, Lazarus etc) variants, pointers can point to program objects such as local or global variables by using '@' e.g @a gives a pointer to the address of the variable a (a can be global or local).

[edit] Expressions

The languages differ significantly when it comes to expression evaluation, C (although not fully comparable) has almost four times as many precedence levels as Pascal.

Pascal has four levels:

  1. Logical negation: not
  2. Multiplicative: * / div mod and
  3. Additive: + - or
  4. Relational: = <> < > <= >= in

while C has 15 levels:

  1. Unary postfix: [] () . -> ++ --
  2. Unary prefix: & * + - ! ~ ++ -- (type) sizeof
  3. Multiplicative: * / %
  4. Additive: + -
  5. Shift: << >>
  6. Relational: < > <= >=
  7. Equality: == !=
  8. Bitwise and: &
  9. Bitwise xor: ^
  10. Bitwise or: |
  11. Logical and: &&
  12. Logical or: ||
  13. Conditional: ? :
  14. Assignment: = += -= *= /= %= <<= >>= &= ^= |=
  15. Comma operator: ,

[edit] Typing

Most operators serve several purposes in Pascal, for instance, the minus sign may be used for negation, subtraction, or set difference (depending on both type and syntactical context), the >= operator may be used to compare numbers, strings, or sets, and so on. C uses dedicated operator symbols to a greater extent.

[edit] Logical connectives

In Pascal a boolean expression that relies on a particular evaluation ordering (possible via side-effects in function calls) is, more or less, regarded as an error. The pascal compiler has the freedom to use whatever ordering it may prefer. It may, for example, use lazy evaluation (jump code) where this is considered "optimal", while employing numerical boolean calculations in other parts of the expression and/or the program.

A C compiler may have a similar freedom in cases where & and | are used instead of && and ||, but it must then also be able to deduce that the boolean result is the sole purpose of the expression and, therefore, that the bitwise value is of no importance, and so can be discarded.

In C, dependence on boolean evaluation order is perfectly legal, and often systematically employed using the && and || operators together with operators such as ++, +=, the comma operator etc. The && and || operators thereby functions as a combination of logical operators and a conditional statement. It is largely this feature (along with its declaration syntax) that has earned C a reputation for being hard to read.

[edit] Control structures

Statements for building control structures are roughly analogous and relatively similar (at least the first three).

Pascal has:

  • if cond then stmt else stmt
  • while cond do stmt
  • repeat stmt until cond
  • for id := expr to expr do stmt
  • case expr of expr : stmt; ... expr : stmt; end

C has:

  • if (cond) stmt else stmt
  • while (cond) stmt
  • do stmt while (cond)
  • for (expr; expr; expr) stmt
  • switch (expr) { case expr : stmt; ... case expr : stmt; default: stmt }

Pascal, in its original form, did not have an equivalent to default, but an equivalent else clause is a common extension. Pascal programmers otherwise had to guard case-statements with an expression such as: if expr not in [A..B] then default-case.

C has the so called early-out statements break and continue, and modern Pascal has them too. There is controversy about whether the inclusion of these statements is in keeping with structured programming methodology. The best that can be said about this is that the use of break and continue may make programming easier, but there is no case where they cannot be replaced by "orthodox" structured programming constructs.

Both C and Pascal have a goto statement. However, since Pascal has nested procedures/functions, jumps can be done from an inner procedure or function to the containing one; this is commonly used to implement error recovery. C has got this capability via the ANSI C setjmp and longjmp. This is equivalent, but arguably less safe.

[edit] Functions/Procedures

In Pascal, routines that return a value are called functions, and routines that don't return a value are called procedures. In C all routines are called functions, however routines that do not return a value are declared to return "void", meaning that they do not return anything. Actually "void" is not really a valid variable type, it can only be used when declaring the return type of a function. It cannot be used for declaring normal variables of this type, for example.

In practice Pascal procedures are equivalent to C functions that return "void", and Pascal functions are equivalent to C functions that return a non-void type.

The following two declarations in C:

int f(int x, int y);
void k(int q);

are equivalent to the following declarations in Pascal:

function f(x, y: integer): integer;
procedure k(q: integer);

In Pascal, there are two different types of parameters, value and pass by reference or VAR parameters. In C, there are only value parameters, but the C ability to point to any variable allows the programmer to construct their own pass by reference scheme:

int f(int *k);
x = f(&t);
function f(var k: integer): integer;

x := f(t);

In C, it is possible to create a function with any number of parameters:

int f(int a, ...);
f(1, 2, 3, 4, 5);

The function f uses a special set of functions that allow it to access each of the parameters in turn. This set of functions was undefined in original C, but was defined in ANSI C. In practice, this feature is easy to call to, but fairly complex, and was machine dependent, to create functions that are called using it. Perhaps because of this, it is mainly used to form the language support library for C, specifically I/O.

Pascal has no equivalent to C's n-parameter feature. However, Pascal has I/O statements built-in to the language, so there is less need for it. Pascal allows procedures and functions to be nested. This is convenient to allow variables that are local to a group of procedures, but not global. C does not have this feature and the localization of variables or functions could only be done for a compilation module wherein the variables or functions would have been declared static.

C allows functions to be indirectly invoked through a function pointer:

int (*cmpar)(char *a, char *b);
char *s1, *s2;
cmpar = &strcmp;
.
.
b = (*cmpar)( s1, s2 );

[edit] Preprocessor

The C language was originally defined as needing a "preprocessor", which was a separate pass that handled constant, type, include and macro definitions to keep memory usage down. This was required since the first C didn't have either constant declarations nor type declarations. However, C obtained those features later with ANSI C.

Pascal wasn't defined with a standardized preprocessor, but several programmers did use it with a preprocessor, sometimes the same one that was used with C. It certainly was not as common as preprocessor use with C, but Pascal had constant and type defines, so the remaining use for the preprocessor was include files and macros.

Although this is often pointed at as a "lack" in Pascal, technically C didn't have program modularity nor macros built in either, and both languages could just as well be equipped with a preprocessor. The alleged problem was that originally there was no standard way of ensuring program modularity or creating macros in Pascal.

As a practical matter, most of the succeeding versions of Pascal used a type controlled modular method instead of include files, so the need for a preprocessor is largely redundant. Include files are sometimes used, but only for special cases, not for the general program structure

[edit] Type escapes

C supports the ability to "cast" a pointer type to another type:

 int a;
 float b;
 
 a = (int) &b;

The meaning of such casts is entirely machine dependent. This feature often helps with low level conversion of data. For example, a floating point value can be output to a file as a series of bytes.

Actually, according to the C Standard this code has undefined effects, and such type casting should be done in a considerably more complicated way:

 union a2c {
   int a;
   float b;
 }
 int a;
 float b;
 union a2c a2c;

 a2c.b = b;
 a = a2c.a;

Although casting is possible on the vast majority of Pascal compilers and interpreters, even in the code below a2c.a and a2c.b aren't required by any Pascal standardizations to share the same address space:

 var a: integer;
     b: real;
     a2c: record
            case boolean of
              false: (a: integer);
              true:  (b: real);
            end;
          end;
 begin
   a2c.b := b;
   a := a2c.a;
 end;

[edit] Files

In C files do not exist as a built-in type (they are defined in a system header) and all I/O takes place via library calls. Pascal has file handling built into the language.

The typical statements used to perform I/O in each language are:

printf("The sum is: %d\n", x);
writeln('the sum is: ', x);

The main difference is that C uses a "format string" that is interpreted to find the arguments to the printf function and convert them, whereas Pascal performs that under the control of the language processor. The Pascal method is arguably faster, because no interpretation takes place, but the C method is highly extensible.

[edit] Modern Pascal Implementations and Extensions

Some popular Pascal implementations have removed virtually all differences with C by incorporating C methods and constructs into Pascal. Examples include type casts, being able to obtain the address of any variable, local or global, and different types of integers with special promotion properties.

However, in languages it is not true that you can have your cake and eat it too. The incorporation of C's cavalier attitude towards types and type conversions can result in a Pascal that loses some of its type security. For example, Java and C# were created in-part to address some of the perceived type security issues of C, and have "managed" pointers that cannot be used to create invalid references. In its original form (as described by Niklaus Wirth), Pascal qualifies as a managed pointer language, some 30 years before either Java or C#. However, a Pascal amalgamated with C would lose that protection.

The Extended Pascal standard extends Pascal to support many things C supports, which the original standard Pascal did not, in a type safer manner. For example, schema types support (besides other uses) variable-length arrays while keeping the type-safety of mandatory carrying the array dimension with the array, allowing automatic run-time checks for out-of-range indices even for dynamically sized array.

[edit] Generated code

Both languages are intended to be easy to compile into efficient machine code. There are three significant differences however.

[edit] Nested procedures with lexical scope

Pascal has nested procedures with lexical scope, which means that the Pascal compiler has to generate code to follow access links embedded in the activation records of procedures (or a faster, so called display). This may hamper performance somewhat under certain circumstances, at least when using a simple compiler which is not capable of factoring out references to non-local variables (via access links).

[edit] Explicit pointers

C programs relies heavily on explicit pointers. Possible pointer aliasing means that optimizations becomes very difficult. Without detailed analysis (also over file boundaries), the compiler must often assume that writes through a pointer may write anywhere. The C convention of traversing arrays via pointers ( *p++ ) instead of using the index operator ( A[i++] ) were perhaps "optimal" on machines like the PDP-8 (were total code size was important), for which the first C implementations were targeted.

[edit] Call mechanism

In C the caller (not the callee) is responsible for removing pushed parameters from the stack after the callee has returned. This is a way to permit (runtime) variable-sized parameter-lists, but it has the side effect of making the generated code somewhat less compact, and therefore less likely to fit into the L1-caches of today's microprocessors (which reduces performance). As a result, most C compilers offer a Pascal-style (or faster still: a register-based "fastcall") calling convention when a function does not take a variable number of parameters.

[edit] Epilogue

It is difficult to produce a truly impartial comparison of C and Pascal, and even more difficult to avoid offending one or another language aficionado.

However, C and Pascal are extraordinarily similar languages, if you look at the basic program structures, data and aims of the two languages. Each time a proponent of C claims that program X cannot be done in Pascal, someone else shows that it can be done. Each time a proponent of Pascal claims that program Y cannot be made machine independent in C, someone else shows that this, too, can be done.

One of the faults with original Pascal that everyone agrees on is the lack of dynamic arrays, which even the creator of Pascal later agreed was not a good idea. Many, or even most later Pascal compilers added an extension for that problem, and the ISO 7185 standard addressed it as well. See Brian Kernighan Why Pascal is Not My Favorite Programming Language

The remaining major difference between the languages that everyone agrees on is type security. This is neither the runaway emergency for C that many claim (you can program array checks in C, you just have to do it yourself), nor the massive lack for Pascal (you can escape types in Pascal, it is just made painful on purpose).

Although C was originally described as a "systems" or "low level" language, it is clearly used for all applications, including high level ones, a fact, or a regrettable fact, depending on your viewpoint!

[edit] Further reading

[edit] See also

C programming language
Libraries: C standard library | glibc | Dietlibc | uClibc | Newlib
History: Criticism of the C programming language
Language Features: String | Syntax | Preprocessor | Variable types and declarations | Functions
Dialects: C++ | Objective-C
C and Other Languages: Compatibility of C and C++ | Operators in C and C++ | Comparison of Pascal and C | C to Java byte-code compiler
Static Wikipedia 2008 (no images)

aa - ab - af - ak - als - am - an - ang - ar - arc - as - ast - av - ay - az - ba - bar - bat_smg - bcl - be - be_x_old - bg - bh - bi - bm - bn - bo - bpy - br - bs - bug - bxr - ca - cbk_zam - cdo - ce - ceb - ch - cho - chr - chy - co - cr - crh - cs - csb - cu - cv - cy - da - de - diq - dsb - dv - dz - ee - el - eml - en - eo - es - et - eu - ext - fa - ff - fi - fiu_vro - fj - fo - fr - frp - fur - fy - ga - gan - gd - gl - glk - gn - got - gu - gv - ha - hak - haw - he - hi - hif - ho - hr - hsb - ht - hu - hy - hz - ia - id - ie - ig - ii - ik - ilo - io - is - it - iu - ja - jbo - jv - ka - kaa - kab - kg - ki - kj - kk - kl - km - kn - ko - kr - ks - ksh - ku - kv - kw - ky - la - lad - lb - lbe - lg - li - lij - lmo - ln - lo - lt - lv - map_bms - mdf - mg - mh - mi - mk - ml - mn - mo - mr - mt - mus - my - myv - mzn - na - nah - nap - nds - nds_nl - ne - new - ng - nl - nn - no - nov - nrm - nv - ny - oc - om - or - os - pa - pag - pam - pap - pdc - pi - pih - pl - pms - ps - pt - qu - quality - rm - rmy - rn - ro - roa_rup - roa_tara - ru - rw - sa - sah - sc - scn - sco - sd - se - sg - sh - si - simple - sk - sl - sm - sn - so - sr - srn - ss - st - stq - su - sv - sw - szl - ta - te - tet - tg - th - ti - tk - tl - tlh - tn - to - tpi - tr - ts - tt - tum - tw - ty - udm - ug - uk - ur - uz - ve - vec - vi - vls - vo - wa - war - wo - wuu - xal - xh - yi - yo - za - zea - zh - zh_classical - zh_min_nan - zh_yue - zu -

Static Wikipedia 2007 (no images)

aa - ab - af - ak - als - am - an - ang - ar - arc - as - ast - av - ay - az - ba - bar - bat_smg - bcl - be - be_x_old - bg - bh - bi - bm - bn - bo - bpy - br - bs - bug - bxr - ca - cbk_zam - cdo - ce - ceb - ch - cho - chr - chy - co - cr - crh - cs - csb - cu - cv - cy - da - de - diq - dsb - dv - dz - ee - el - eml - en - eo - es - et - eu - ext - fa - ff - fi - fiu_vro - fj - fo - fr - frp - fur - fy - ga - gan - gd - gl - glk - gn - got - gu - gv - ha - hak - haw - he - hi - hif - ho - hr - hsb - ht - hu - hy - hz - ia - id - ie - ig - ii - ik - ilo - io - is - it - iu - ja - jbo - jv - ka - kaa - kab - kg - ki - kj - kk - kl - km - kn - ko - kr - ks - ksh - ku - kv - kw - ky - la - lad - lb - lbe - lg - li - lij - lmo - ln - lo - lt - lv - map_bms - mdf - mg - mh - mi - mk - ml - mn - mo - mr - mt - mus - my - myv - mzn - na - nah - nap - nds - nds_nl - ne - new - ng - nl - nn - no - nov - nrm - nv - ny - oc - om - or - os - pa - pag - pam - pap - pdc - pi - pih - pl - pms - ps - pt - qu - quality - rm - rmy - rn - ro - roa_rup - roa_tara - ru - rw - sa - sah - sc - scn - sco - sd - se - sg - sh - si - simple - sk - sl - sm - sn - so - sr - srn - ss - st - stq - su - sv - sw - szl - ta - te - tet - tg - th - ti - tk - tl - tlh - tn - to - tpi - tr - ts - tt - tum - tw - ty - udm - ug - uk - ur - uz - ve - vec - vi - vls - vo - wa - war - wo - wuu - xal - xh - yi - yo - za - zea - zh - zh_classical - zh_min_nan - zh_yue - zu -

Static Wikipedia 2006 (no images)

aa - ab - af - ak - als - am - an - ang - ar - arc - as - ast - av - ay - az - ba - bar - bat_smg - bcl - be - be_x_old - bg - bh - bi - bm - bn - bo - bpy - br - bs - bug - bxr - ca - cbk_zam - cdo - ce - ceb - ch - cho - chr - chy - co - cr - crh - cs - csb - cu - cv - cy - da - de - diq - dsb - dv - dz - ee - el - eml - eo - es - et - eu - ext - fa - ff - fi - fiu_vro - fj - fo - fr - frp - fur - fy - ga - gan - gd - gl - glk - gn - got - gu - gv - ha - hak - haw - he - hi - hif - ho - hr - hsb - ht - hu - hy - hz - ia - id - ie - ig - ii - ik - ilo - io - is - it - iu - ja - jbo - jv - ka - kaa - kab - kg - ki - kj - kk - kl - km - kn - ko - kr - ks - ksh - ku - kv - kw - ky - la - lad - lb - lbe - lg - li - lij - lmo - ln - lo - lt - lv - map_bms - mdf - mg - mh - mi - mk - ml - mn - mo - mr - mt - mus - my - myv - mzn - na - nah - nap - nds - nds_nl - ne - new - ng - nl - nn - no - nov - nrm - nv - ny - oc - om - or - os - pa - pag - pam - pap - pdc - pi - pih - pl - pms - ps - pt - qu - quality - rm - rmy - rn - ro - roa_rup - roa_tara - ru - rw - sa - sah - sc - scn - sco - sd - se - sg - sh - si - simple - sk - sl - sm - sn - so - sr - srn - ss - st - stq - su - sv - sw - szl - ta - te - tet - tg - th - ti - tk - tl - tlh - tn - to - tpi - tr - ts - tt - tum - tw - ty - udm - ug - uk - ur - uz - ve - vec - vi - vls - vo - wa - war - wo - wuu - xal - xh - yi - yo - za - zea - zh - zh_classical - zh_min_nan - zh_yue - zu