0% found this document useful (0 votes)
95 views12 pages

Evolution of Programming Languages

C++ is a significantly more powerful language - but is significantly bigger and more complicated personal taste and experience. Strongly typed languages better control of structure of really large programs better internal checks, organization, safety Why C++ first? historical sequence - C++ tries to remedy drawbacks and limitations of C - Java reacts to size and complexity of C++ compatibility with C - source and object mechanisms are visible and controllable - classes have zero overhead in simplest cases - classes are not mandatory - garbage collection

Uploaded by

api-3749401
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
95 views12 pages

Evolution of Programming Languages

C++ is a significantly more powerful language - but is significantly bigger and more complicated personal taste and experience. Strongly typed languages better control of structure of really large programs better internal checks, organization, safety Why C++ first? historical sequence - C++ tries to remedy drawbacks and limitations of C - Java reacts to size and complexity of C++ compatibility with C - source and object mechanisms are visible and controllable - classes have zero overhead in simplest cases - classes are not mandatory - garbage collection

Uploaded by

api-3749401
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 12

Evolution of Programming Languages

• 40's machine level


– raw binary

• 50's assembly language


– names for instructions and addresses
– very specific to each machine

• 60's high-level languages


– Fortran, Cobol, Algol

• 70's system programming languages


– C
– Pascal (more for teaching structured programming)

• 80's object-oriented languages


– C++, Ada, Smalltalk, Modula-3, Eiffel, …
strongly typed languages
better control of structure of really large programs
better internal checks, organization, safety

• 90's "scripting", Web, component-based, …


– Java, Visual Basic, Perl, …
strongly-hyped languages
focus on interfaces, components

Why C++ first? Why not Java?

• historical sequence
– C++ tries to remedy drawbacks and limitations of C
– Java reacts to size and complexity of C++

• compatibility with C
– source and object

• mechanisms are visible and controllable, e.g.,


– classes have zero overhead in simplest cases
– classes are not mandatory
– garbage collection is not automatic but can be
programmed
– can use C I/O or define a new one

• C++ is a significantly more powerful language


– but is significantly bigger and more complicated

• personal taste and experience

1
Stacks in C: a single stack
int stack[100];
int *sp = stack; /* first unused */

#define push(n) (*sp++ = (n))


#define pop() (*--sp)

for (i = 0; i < 10; i++)


push(i);

Stacks in C: a stack type


typedef struct {
int stk[100];
int *sp;
} stack;

int push(stack s, int n) {


return *s.sp++ = n;
}

int pop(stack s) {
return *--s.sp;
}

stack s1, s2;


for (i = 0; i < 10; i++)
push(s1, i);

2
Another stack implementation
typedef struct {
int *stk;
int *sp;
} stack;

int push(stack *s, int n) {


return *s->sp++ = n;
}
int pop(stack *s) {
return *--s->sp;
}

stack *s1, *s2; not initialized


s1->stk =
(int *) malloc(100 * sizeof(int));
ugly
for (i = 0; i < 10; i++)
push(*s1, i);

Problems

• representation is visible, can't be protected


(e.g., s1->stk)
• creation and copying must be done very carefully
– and you don't get any help with them
• no initialization
– you have to remember to do it
• no help with deletion
– you have to recover the memory when not in use
• weak argument checking between declaration and
call
– easy to get inconsistencies

• the real problem: no abstraction mechanisms


– complicated data structures can be built,
but access to the representation can't be controlled
– you can't change your mind once the first
implementation has been done

• abstraction and information hiding are


nice for small programs
absolutely necessary for big programs

3
C++

• designed & implemented by Bjarne Stroustrup


Bell Labs (1979-95) -> AT&T Labs (1995-)
– began ~ 1980; ISO standard 1998

• a better C
– more checking of interfaces (ANSI C)
– other features for easier programming
• data abstraction
– you can hide HOW something is done in a program,
– reveal only WHAT is done
– HOW can be safely changed as program evolves
• object-oriented programming
– inheritance -- new types can be defined that inherit
properties from previous types
– polymorphism or dynamic binding -- function to be
called is determined by data type of specific object
at run time
• parameterized types
– define families of related types, where the type is a
parameter
– templates or "generic" programming

C++ classes

• data abstraction and protection mechanism


derived from Simula 67 (Kristen Nygaard, Norway)

class thing {
public:
methods -- functions that define what operations can be
done on this kind of object
private:
variables and functions that implement the operations
};

• defines a data type 'thing'


– can declare variables and arrays of this type, create
pointers to them, pass them to functions, return
them, etc.
• object: an instance of a class variable
• method: a function defined within the class

• private variables and functions are not accessible


from outside the class
• it is not possible to determine HOW the
operations are implemented, only WHAT they do.

4
C++ synopsis
• data abstraction with classes
– a class defines a type that can be used to
declare variables of that type,
control access to representation

• operator and function name overloading


– all C operators (including assignment, ( ), [ ], ->,
argument passing and function return) can be
overloaded so they apply to user-defined types
• control of creation and destruction of objects
– initialization of class objects
– recovery of resources on destruction
• inheritance: derived classes built on base classes
– virtual functions override base functions
– multiple inheritance: inherit from more than one class
• exception handling
• namespaces for separate libraries
• templates (generic types)
• Standard Template Library
– generic algorithms on generic containers

• compatible (almost) with C


– except for new keywords

Stack class in C++

// stk1.c: stack of ints, 1st draft; no checking!!!

class stack {
private: // this is the default
int stk[100];
int *sp; // next free place
public:
int push(int);
int pop();
};

int stack::push(int n) // push n onto stack


{
return *sp++ = n;
}

int stack::pop() // pop top element


{
return *--sp;
}

5
Testing stk1.c

#include <stdio.h>

main()
{
stack s;
int i;

for (i = 0; i < 10; i++)


s.push(i);
for (i = 0; i < 10; i++)
if (s.pop() != 9-i)
printf("oops: %d\n", i);
}

$ CC -g stk1.c (or g++ -g stk1.c)


$ a.out

Constructors: making a new object

// stk2.c: constructors

class stack {
private:
int stk[100];
int *sp; // next free place
public:
stack(); // constructor
int push(int);
int pop();
};

stack::stack() { sp = stk; }

int stack::push(int n) // push n onto stack


{
return *sp++ = n;
}
int stack::pop() // pop top element
{
return *--sp;
}

6
Testing stk2.c

main()
{
stack s1, s2;
int i;

for (i = 0; i < 10; i++)


s1.push(i);
for (i = 0; i < 10; i++)
s2.push(s1.pop());
for (i = 0; i < 10; i++)
if (s2.pop() != i)
printf("oops: %d\n", i);
}

Memory allocation: new and delete

• new is a type -safe alternative to malloc


– delete is the matching alternative to free
• new T allocates an object of type T, returns
pointer to it
stack *sp = new stack;
• new T[n] allocates array of T's, returns pointer
to first
int *stk = new int[100];
– by default, throws exception if no memory
• delete p frees the single item pointed to by p
delete sp;
• delete [ ] p frees the array beginning at p
delete [ ] istk;

• new uses T's constructor for objects of type T


– need a default constructor for array allocation
• delete uses T's destructor ~T()

• use new/delete instead of malloc/free


– malloc/free provide raw memory but no semantics
– this is inadequate for objects with state
– never mix new/delete and malloc/free

7
Dynamic stack with new, delete
// stk3.c: new, destructors, delete; explicit size

class stack {
private:
int *stk; // allocated dynamically
int *sp; // next free place
public:
stack(); // constructor
stack(int n); // constructor
~stack(); // destructor
int push(int);
int pop();
};

stack::stack()
{
stk = new int[100]; sp = stk;
}

stack::stack(int n)
{
stk = new int[n]; sp = stk;
}

stack::~stack() { delete [ ] stk; }

Where are we?

• a class is a user-defined type


• an object is an instance (variable or value) of
that type
• public part defines interface it supports
– member functions in the public part define legal
operations on an object
• private part defines implementation
– functions and data values that implement interface
• constructors are members that define how to
create new instances
• destructor is a member that defines how to
destroy an instance ( e.g., how to recover its resources )

• there's more to constructors


– show up implicitly in declarations, function arguments,
return values, assignment
– the meaning of explicit and implicit copying must be
part of the representation

8
Inline definitions, default arguments
// stk4.c: inline definitions, default size

class stack {
int *stk; // allocated dynamically
int *sp; // next free place
public:
stack(int n);
~stack() { delete [ ] stk; }
int push(int n) { return *sp++ = n; }
int pop() { return *--sp; }
int top() { return sp[-1]; }
};
inline stack::stack(int n = 100)
{ // ^ default argument
stk = new int[n];
sp = stk;
}

main() {
stack s1(10), s2;

// could use 2 constructors instead of default arg


// stack(); stack(int n);

Overloaded functions / default args

• default arguments: syntactic sugar for a single


function
stack::stack(int n = 100);
• declaration can be repeated if the same

• explicit size in call


stack s(500);
• omitted size uses default value
stack s;

• overloaded functions: different functions,


distinguished by argument types
• these are two different functions:
stack::stack(int n);
stack::stack();

9
Change of representation

// stk5.c: change of representation (no checking)

class stack {
private:
struct blk { // private to this class
int n;
blk *nb;
blk(int sz = 0, blk *next = 0);
};
blk *sp; // top == head of the list

public:
stack(int = 0) { sp = 0; }
~stack() { while (sp) pop(); }
int push(int n);
int pop();
int top() { return sp->n; }
};

Representation as linked list


stack::blk::blk(int sz, blk *next)
{
n = sz;
nb = next;
}

int stack::push(int n)
{
blk *bp = new blk(n, sp);
sp = bp;
return n;
}

int stack::pop()
{
blk *bp = sp;
int n = sp->n;
sp = sp->nb;
delete bp;
return n;
}

10
Aside on implementation

• a class is just a struct


– no overhead
– no "class Object" that everything derives from
– member functions are just names
– definition is such that C++ can be translated into C
– original C++ compiler was a C++ program ("cfront")
that generated C

struct stack { /* sizeof stack == 8 */


int *stk__5stack ;
int *sp__5stack ;
};
...
struct stack __1s1 ;
struct stack __1s2 ;
int __1i ;
...

Cfront output, continued...


main() {
stack s1(10), s2;
int i;
for (i = 0; i < 10; i++)
s1.push(i);
for (i = 0; i < 10; i++)
s2.push(s1.pop());
for (i = 0; i < 10; i++)
if (s2.pop() != i)
printf("oops: %d\n", i);
}

( (( ((& __1s1 )-> stk__5stack = (((int *)__nw__FUi (


(sizeof (int ))* 10 ) ))), ((& __1s1 )-> sp__5stack =
(& __1s1 )-> stk__5stack )) ), (((& __1s1 )))) ;
( (( ((& __1s2 )-> stk__5stack = (((int *)__nw__FUi (
(sizeof (int ))* 100 ) ))), ((& __1s2 )-> sp__5stack =
(& __1s2 )-> stk__5stack )) ), (((& __1s2 )))) ;
for(__1i = 0 ;__1i < 10 ;__1i ++ )
( (((*((& __1s1 )-> sp__5stack ++ )))= __1i )) ;
for(__1i = 0 ;__1i < 10 ;__1i ++ )
( (__2__X1 = ( ((*(-- (& __1s1 )-> sp__5stack )))) ), (
(((*((&__1s2 )-> sp__5stack ++ )))= __2__X1 )) ) ;
for(__1i = 0 ;__1i < 10 ;__1i ++ )
if (( ((*(-- (& __1s2 )-> sp__5stack )))) != __1i )
printf ( (char *)"oops: %d\n",__1i ) ;
( (( ( __dl__FPv ( (char *)(& __1s2 )-> stk__5stack ) ,
(( (( 0 ) ), 0 ))) , 0 ) )) ;
( (( ( __dl__FPv ( (char *)(& __1s1 )-> stk__5stack ) ,
(( (( 0 ) ), 0 ))) , 0 ) )) ;

11
Where are we now?

• hiding representation with private


• member functions for public interface
– classname :: member()
• constructors to make new instances and initialize
them
• destructors to delete them cleanly
• change of representation
– as long as the public part doesn't change
• nothing magic about implementation

What we have ignored (besides error checking):

• implications of assignment and initialization


– declarations, function arguments, function return
values
– if we don't do anything, will get memberwise
assignment and initialization

The meaning of explicit and implicit copying MUST


be part of the representation

12

You might also like

pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy