
Guiding Philosophy
1. Programming Languages for People
Programming languages are how humans communicate with computers. The computer is happy to converse in any language that is unambiguous. The reason we have high-level languages is that humans cannot cope with machine language. The essence of programming languages is to prevent our fragile human brain from being overwhelmed by a mass of details.
Architects know that some design problems are more grounded than others. Some of the clearest and most abstract design problems involve building bridges. In this case, your job is to span the required distance using the least amount of material. On the other end of the spectrum is designing chairs. Chair designers must spend their time thinking about human backsides.
Software development has a similar distinction. Designing algorithms for routing data through a network is a good, abstract problem, much like designing bridges. Meanwhile, designing programming languages is akin to chair design: it must contend with human shortcomings.
Most of us find this hard to acknowledge. Designing elegant mathematical systems sounds so much more appealing to most of us than accommodating human weaknesses. The role of mathematical elegance is that a certain degree of elegance makes programs easier to comprehend. But elegance is not the only consideration.
And when I say languages should be designed to account for human weaknesses, I do not mean that languages should be designed for poor programmers. In fact, you should design software for the best programmers, but even the best programmers have their limits. I donât think anyone would enjoy programming in a language where all variables were labeled with the letter 'x' with integer indices.
2. Design for Yourself and Your Friends
If you look at the history of programming languages, most of the best languages were designed for their creatorsâ own use, while most of the worst were designed for other people.
When languages are designed for other people, itâs always for a specific group: people arenât as smart as the language creators. This results in a language that talks down to you. Cobol is the most prominent example, but most languages are permeated by this spirit.
This has nothing to do with how high-level a language is. C is fairly low-level, but it was created for its authorsâ use, which is why hackers love it.
The argument for designing languages for poor programmers is that there are more poor programmers than good ones. Perhaps thatâs true. But a small number of good programmers write disproportionately more software.
Iâm interested in the question of how to create a language that appeals to the best hackers. I think this question is the same as how to create a good programming language, but even if itâs not, itâs at least an interesting question.
3. Give the programmer as much control as possible
Many languages (especially those created for other people) act like babysitters: they try to warn you away from things they think wonât be beneficial. I hold the opposite view: give the programmer as much control as you can.
When I first learned Lisp, what I liked most was that we spoke as equals. In other languages I had learned by that time, there was the language and there was my program in that language, and they existed quite separately. But in Lisp, the functions and macros I wrote were the same ones on which the language itself was built. I could rewrite the language itself if I wanted. It had the same appeal as open-source software.
4. Brevity is the soul of talent
Brevity is often undervalued and even despised. But if you look into the hearts of hackers, you'll see that they cherish brevity. How many times have you heard hackers fondly speak about how, in APL, they can do amazing things with just a few lines of code? I believe that truly smart people actually appreciate this.
I believe that nearly everything that allows for shorter programs is a good thing. There should be plenty of library functions, everything that can be implicit should be so; the syntax should be more concise; even entity names should be short.
And it's not just programs that should be short. Manuals should be short as well. A good portion of manuals is filled with explanations, caveats, warnings, and special cases. If you need to shorten a manual, the best way is to fix the language that requires so many explanations.
5. Acknowledge what hacking is
Many people wish that hacking were like mathematics or, at least, something akin to the natural sciences. I think that hacking is more like architecture. Architecture is related to physics, in the sense that an architect needs to design a building that wonât fall down, but the true goal of an architect is to create a great building, not to make discoveries in the realm of statics.
What hackers love is creating great programs. And I think, at least in our own minds, we should remember that writing outstanding programs is remarkable, even when this work doesnât easily translate into the usual intellectual currency of academic papers. From an intellectual standpoint, it is equally important to develop a language that programmers will love as it is to create a terrible one that embodies the idea, about which you can publish an article.
Open problems
1. How to organize large libraries?
Libraries are becoming an important part of programming languages. They are growing so large that this can be dangerous. If it takes longer to find a function in a library that meets your needs than to write the function yourself, then all the code does is clutter your manual. (The Symbolics manuals were an example of this.) So, we need to solve the problem of library organization. Ideally, they should be designed so that a programmer could guess which library function would be suitable.
2. Are people really scared of prefix syntax?
This is an open question in the sense that I've been thinking about it for several years and still don't know the answer. Prefix syntax seems absolutely natural to me, except perhaps for its use in mathematics. But it could be that a large part of Lisp's unpopularity is simply due to unfamiliar syntax⊠Whether something should be done about this, if it's true, is another question.
3. What do you need for server software?
I believe that most applications written in the next twenty years will be web applications, in the sense that programs will be hosted on a server and will communicate with you through a web browser. And in order to write such applications, we need new things.
One of those things is support for a new way of releasing server applications. Instead of one or two large releases a year, like desktop software, server software will be released in a series of small changes. You could have five or ten releases a day. And everyone will always have the latest version.
Do you know how to design programs to be maintainable? Server software should be designed to be adaptable. You should have the ability to change it easily, or at least know what constitutes a minor change and what is significant.
Another thing that can be useful in server software is, unexpectedly, continuous delivery. In a web application, you can use something like , to achieve the effect of subprograms in a stateless world of web sessions. Continuous delivery could be worth it if the capability is not too expensive.
4. What new abstractions are left to discover?
I am not sure how reasonable such hope is, but personally, I would very much like to open a new abstraction â something that could hold as much significance as first-class functions or recursion, or at least default parameters. Perhaps this is an unattainable dream. Such things are often not discovered. But I do not lose hope.
Little-known secrets
1. You can use any language you wish
In the past, creating applications meant developing desktop software. And with desktop software, there was a strong tendency to write applications in the same language as the operating system. So ten years ago, writing software generally meant writing it in C. Eventually, that tradition evolved: applications don't have to be written in uncommon languages. This tradition has developed for so long that even non-technical people, such as managers and venture capitalists, have learned this.
Server-side software completely destroys this model. With server-side software, you can use any language you want. Almost nobody understands this yet (especially managers and venture capitalists). But some hackers do understand, which is why we've heard about indie languages like Perl and Python. We don't hear about Perl and Python because people use them to write applications for Windows.
What this means for us, people interested in designing programming languages, is that there is a potential audience for our work.
2. Speed comes from profilers
Language developers or, at least, their implementers enjoy writing compilers that generate fast code. But I believe that this does not make languages fast for users. Knuth noted long ago that speed depends on only a few bottlenecks. And anyone who has tried to speed up a program knows that you cannot guess where the bottleneck is. The profiler is the answer.
The language developers are not addressing the right issue. Users don't need benchmarks to run quickly; they need a language that can show which parts of their program need to be rewritten. At that moment, speed is needed in practice. So it might be better if language implementers spent half the time they spend optimizing the compiler on writing a good profiler instead.
3. You need an application that drives your language's development.
This may not be the ultimate truth, but it seems that the best languages have evolved alongside the applications in which they are used. C was created by people who needed system programming. Lisp was developed partly for symbolic differentiation; McCarthy was so eager to begin that he started writing differentiation programs even in the first document about Lisp in 1960.
This is especially beneficial if your application addresses some new problems. It encourages your language to have new features that programmers need. Personally, I am interested in writing a language that is good for server applications.
[During the discussion, Guy Steele also expressed this thought, adding that an application should not consist of writing a compiler for your language unless your language is specifically designed for writing compilers.]
4. A language should be suitable for writing throwaway programs.
You know what a throwaway program means: it's when you need to quickly solve a limited problem. I believe that if you look around, you will find many serious programs that started as throwaway ones. I wouldn't be surprised if most programs began as throwaway. Therefore, if you want to create a language that is suitable for writing software in general, it should also be suitable for writing throwaway programs, as this is the starting stage for many programs.
5. Syntax is tied to semantics.
It is traditionally believed that syntax and semantics are vastly different things. This may sound shocking, but that's not the case. I think what you want to achieve in your program is connected to how you express it.
Recently, I spoke with Robert Morris, and he pointed out that operator overloading is a great advantage for languages with infix syntax. In languages with prefix syntax, any function you define is actually an operator. If you want to add a new type of number that you've invented, you can simply define a new function for its addition. If you do this in an infix syntax language, you will see a significant difference between using an overloaded operator and calling a function.
Ideas that come back over time
1. New programming languages
Looking back to the 1970s, it was fashionable to develop new programming languages. That's not the case now. However, I believe that server software will bring the creation of new languages back into vogue. With server software, you can use any language you want, so if someone creates a language that seems better than the rest, there will be people willing to use it.
2. Time-sharing
Richard Kelsey proposed this idea whose time has come again, and I completely support it. My assumption (and Microsoft's as well) is that many computations will move from desktops to remote servers. In other words, time-sharing has returned. I believe that support for this at the language level will be necessary. For example, Richard and Jonathan Reeves did a lot of work to implement process scheduling in Scheme 48.
3. Efficiency
Recently, it seemed that computers were already fast enough. More and more, we are hearing about bytecode, which at least for me means that we have spare power. But I think that with server software, we donât have that. Someone will have to pay for servers, on which the software runs, and the number of users that the server can handle per machine will be a divisor of their capital costs.
I believe that efficiency will matter, especially in bottlenecks of computation. This will be particularly important for input-output operations, as server applications perform many such operations.
Ultimately, it may turn out that byte code is not the solution. Sun and Microsoft currently seem to be battling it out on the byte code front. But they are doing this because byte code is a convenient space to embed themselves in the process, not because byte code is inherently a good idea. This entire battle might end up going unnoticed. It would be amusing.
Traps and Pitfalls
1. Clients
This is only a guess, but it is that only those applications that will be fully server-based will win. Designing software that operates under the assumption that everyone will have your client resembles creating a society based on the assumption that everyone will be honest. It would certainly be convenient, but you have to concede that this will never happen.
I anticipate a rapid increase in devices with web access, and it can be assumed that they will support basic HTML and forms. Do you have a browser on your phone? Will your PalmPilot have a phone? Will your Blackberry have a larger screen? Will you be able to go online from your Game Boy? From your watch? I don't know. And I won't have to find out if I bet that everything will be server-based. It's simply much more reliable to have all the brains on the server.
2. Object-Oriented Programming
I understand that this is a controversial statement, but I don't believe that OOP is of great importance. I think it is a suitable paradigm for specific applications that require specialized data structures, like window systems, simulations, and CAD systems. But I don't understand why it should be suitable for all programs.
I think people in large companies like OOP, partly because it offers much of what looks like work. What can naturally be represented as, say, a list of integers, can now be represented as a class with all kinds of scaffolding, noise, and fuss.
Another appealing aspect of OOP is that methods give you some effect of first-class functions. But this is not new to Lisp programmers. When you have true first-class functions, you can simply use them in any way that suits the task at hand instead of forcing everything into a template of classes and methods.
I think this means for language design that you shouldn't embed OOP too deeply into it. Perhaps the answer is to offer more general, foundational concepts and allow people to design any object systems in the form of libraries.
3. Committee Design
If your language is designed by a committee, then you are trapped, and not just for reasons that are well known. It is well known that committees tend to create a clunky, inconsistent language design. But I believe the greater danger is that they do not take risks. When one person is in charge, they take risks that a committee would never agree to take on.
Is it necessary to take risks to create a good language? Many people might suspect that language design is one area where you should stick quite closely to traditional wisdom. I would argue that this is not the case. In everything else that people do, the reward is proportional to the risk. So why should language design be any different?
Source: habr.com
