In our study of program design, we have seen that expert programmers control the complexity of their designs with the same general techniques used by designers of all complex systems. In illustrating these techniques, we have used Lisp as a language for describing processes and for constructing computational data objects and processes to model complex phenomena in the real world. However, as we confront increasingly complex problems, we will find that Lisp, or indeed any fixed programming language, is not sufficient for our needs. We must constantly turn to new languages in order to express our ideas more effectively.
Programming is endowed with a multitude of languages.
There are physical languages, such as the machine languages for particular computers. These languages are concerned with the representation of data and control in terms of individual bits of storage and primitive machine instructions. These languages have means of combination and abstraction, such as procedure definition, that are appropriate to the larger-scale organization of systems. It is particularly important to computer programming, because in programming not only can we formulate new languages but we can also implement these languages by constructing evaluators. To appreciate this point is to change our images of ourselves as programmers.