Programming Language
Put two humans together, and you get language. Put a human and a computer together, and you get a new programming language. We can't help but invent symbols and combine them in formulaic ways in order to communicate. Even if an existing language is given to us, we modify it with shortcuts and new structures. We are so quick to shape our languages that some cognitive scientists believe language is instinctual, rooted not just in culture but our very biology.
Nevertheless, we live in the days of graphical applications and LLMs, and we may rightly wonder if our language instinct is obsolete. Is learning about or inventing new languages—human or programming—a good use of our time? Why write formal code when we can click a button or drag a slider or write a prompt in natural language? Several programming language researchers think that languages still have a place in our toolbelts:
While both GUIs and languages are often designed around making it easy for users to say common things, a language empowers users to say uncommon things too.
Languages, graphical user interfaces, and LLMs are all interfaces to computation, but they sit at different levels of abstraction. Sometimes we want to operate at a high-level of abstraction, but not always. We want all our choices.
People who publish books are called writers, but really their job is to think. The tasks of writing and thinking are hard to separate. If writers think but don't write, their thoughts are lost. And they usually don't know what they think until they start writing. So it is with us. We call ourselves programmers, but really our job is to build technologies. We don't get technologies without code, and we come to understand technology by programming. If we want new and better technologies, we should not abandon programming languages.
In this chapter, we continue exploring these ideas by examining programming languages as a subdiscipline of computer science. We'll continue using Ruby, but our subject is bigger than any particular language. By the end of this chapter, you'll have first-draft answers to these questions:
- Why are there so many programming languages and why do we study them?
- How does a program written in a high-level language get turned into a form that the CPU can execute?
- How do we describe the syntax of a new language so that others can understand it?
- What algorithms will take us from source code to an abstract syntax tree?
In the last chapter, we started looking at Ruby. We'll keep using Ruby in this chapter, but our focus is on building a brand new programming language. We will decide what it looks like and what it does. And we'll build the tools that translate programs written in this unknown language into a known language that the CPU can execute.