Eiffel in Computer Science Education
James Heliotis
Rochester Institute of Technology
1. Background
A generation ago, the view of the student of computer science was very different than it is today. First, it should be pointed out, there were very few bachelors degrees being offered in computer science. Most computing majors were in engineering or mathematics, and simply specialized in programming. But more significant was the view that academia had of computer scientists. They were the ones who programmed the computers, and they as a group were one of its major users. If you were interested in computers, and wanted a chance to use them on a regular basis, then you would study computer science, or perhaps traditional engineering or other scientific fields. Using a computer for original work often involved programming, and only those brilliant people who could master a programming language could do it.
Today, the landscape is very different. Here at the Rochester Institute of Technology, all faculty and students, and most staff, use computers in their regular work. Our university, like many around the world, has an infrastructure that includes a data communications network with outlets in most offices, classrooms, and dormitory rooms. Personal computers or workstations can be found in almost all faculty offices, while user areas containing terminals and individual computing stations, are found throughout the campus. Besides the traditional uses of computing in engineering and science disciplines, students use computers to do things like scan the library's resources, compose their term papers, and use our connection to the Internet to do research in every imaginable field.
Where, then, does this leave the discipline traditionally known as Computer Science? Obviously, the students in our programs are no longer the guardians of the sacred machines. For some universities, this causes an increase in activity in the theoretical areas of our field, and in research into new architectures and paradigms for computing. Because RIT's emphasis has always been more towards the preparation of a student for a career (not a first job) in the commercial environment, and because the size and complexity of software systems seems to be growing faster than our ability to organize and control their design, it became clear to us that a pedagogical change was needed. We had to stop teaching students how to program, and start teaching them how to develop software.
2. Curriculum Goals
Our new curriculum, delivered for the first time in the fall of 1994, stressed several new things:
The three candidate languages that made our "short list" were Modula-3, Smalltalk, and Eiffel. After scoring each language the best we could against the properties enumerated above, and weighing the importance of each property. We chose, with some apprehension, Eiffel as our new "first language".
3. Results
All of us involved in teaching the first year courses agree that Eiffel has far exceeded our expectations. In this section I will list the benefits that we have discovered in using the language over the last year and a half.
Simplicity
The grammar, and even much of the semantics, of the language is quite simple. Here are some reasons why:
Eiffel The Language [Mey92] contains a four-page set of syntax diagrams. This is far shorter than any other strongly typed object-oriented (OO) language with which I have worked. One amazing example of this is that semicolons are not needed after statements! In addition, Eiffel has a uniform "look and feel", if you will. All compound constructs (class, routine, if block, loop, debug, ...) follow the same pattern: a sequence of sections, each beginning with a keyword; the entire construct ends with the keyword end. The terse Eiffel language reference manual is 142 pages. Compare that with C++, for example, whose ANSI draft standard is over 700 pages!
There is almost never more than one way to do something in the language. This is true of iterative loops, creating objects, and returning an object from a function routine. Although more experienced programmers may miss some of their favorite "tricks", it makes learning the language a lot easier. It also shrinks the compiler, and simplifies the task of optimization.
The inheritance model is quite intuitive, unless you are used to another. We make students aware of inheritance from the start, but do not have them use it in design until the second half of the year. The only exception to this may be the incantations one must perform to invoke the creation routine of an ancestor class. Expect to take time on this one bit of knowledge! One language feature that ended up being far more useful than we expected was the anchor type. Without this tool, and other aspects of the language that allow for type covariance, inheritance is far less useful.
The memory management system is easy to work with, since all objects are garbage collected. This allows manual memory management to be taken up as a separate topic in a more advanced course. In the meantime, students are not distracted having to think about dangling pointers, the difference between a value and a reference to a value, and which object should have the responsibility of freeing up another object's space.
Many OO languages tend to require separate files for interface and implementation. This is tedious work for programmers, who must write the same code twice, and then maintain those two copies. The Eiffel language requires but one class description, the complete one. Tools that come with the compiler provide the different views needed by users and implementors.
OOD and OOP
Our first year courses now stress design as a distinguishable task. Obviously, any OO language will help teach design because of the way they tend to reveal design principles such as encapsulation and interfaces.
Eiffel goes beyond this by enforcing, through language constructs, the design principle known as design by contract. Each supplier must define its routines' names and parameter lists, of course. In addition, however, the programmer is expected to describe the semantics of each routine by specifying preconditions, things expected of the client, and post conditions, things promised by the supplier.
Relating back to simplicity, a simple programming language permits the use of a simple design notation. One need not invent notation to illustrate subtle differences in the ways attributes, associations, or methods end up being written during implementation. We have done quite well with just a class bubble, connectors for client-supplier and inheritance, a way to enumerate class features, and a tag for abstract classes and their deferred routines.
4. A Change in Pedagogy
As a way of concluding, I will remark on how Eiffel and the Eiffel tools we use have enabled us to change the way we teach introductory computer science.
Thanks to existing libraries full of all kinds of useful data structures, we no longer need to instruct students how to build something before they may use it. In the first five months, they learn how to use linked lists, stacks, queues, trees, and arrays. They learn notions of abstraction, like how linked lists and arrays can be used interchangeably in some applications, but with different efficiency, or how queues and stacks share a common interface, known in our library as the abstract class DISPENSER. Early in the second year, we revisit some of these handy structures and investigate their implementations.
Eiffel makes it easier to take a complex software system and "open it up" slowly, piece by piece. In the first quarter, the students are introduced to a graphical card solitaire game. In one laboratory, they are asked to make trivial modifications to the program under our guidance. Later on, they revisit the program and add a new feature with very few perturbations to the existing code. (This is an example of the belief in the OO community that top-down design creates inflexible systems, but OO designs tend to easily adapt to changes in the requirements. [Mey88]). In the second quarter, they use the generic card game framework to build a completely new solitaire game.
Because we started with a pure OO language, the teaching of other OO languages later in the curriculum becomes much easier. The students are also less tempted to stray from the OO implementation techniques we have taught them, since that is all they know. Some academics have expressed concern that we who teach objects first have simply reversed the problem. Whereas it was once hard to learn OO languages after being trained in the imperative paradigm, students will now struggle to write in procedural languages. Well, it may help to remember that a C program can be described as just one huge object!
In summary, were I asked to come up with a few words that explain our tremendous satisfaction with Eiffel as a teaching language for computing, I would choose simplicity and reuse. The former word says that we can get through the more tedious parts of programming instruction quickly, and spend more time on the good stuff; the latter says that we can give the students interesting applications from the beginning, and give them more assignments that build on previous work than ever before. Our students' comments confirm our appraisal.
If you are in the market for a programming language to be used in the teaching of software development, I strongly recommend Eiffel. It deserves a close look.
Bibliography
[Mey88] Meyer, Bertrand, Object-Oriented Software Construction, Prentice-Hall, 1988
[Mey92] Meyer, Bertrand, Eiffel The Language, Prentice-Hall, 1992