Dominus talks about HO Perl

Via Xavier Noria, an interview with Mark Jason Dominus in the Perl review, mostly about Higher-Order Perl [2].

Don't get too overheated...

Postscript: Add your links to this subnode.

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.

Cool interview

No overheating here, I agree with most of what Mark Jason Dominus says — we need more people like that out there.

For those who haven't already seen it, his Perl contains the Lambda Calculus is fun.

Agree

...though he was stretching his artistic license to its seams while talking about monads.

OTOH, I am not happy with appearance of Strong Turing thesis in the LC article you cited.

Artistic license

...though he was stretching his artistic license to its seams while talking about monads.

Really? I put some effort into that phrase, and I thought I had done a good job of characterizing monads in one sentence for the audience for which I was writing. When you write an article like this, you have to consider what the audience will receive, not just what you send, and adjust the message accordingly. For example, I could have talked about category theory, and perhaps that discussion would have been more correct when I transmitted it, but I think that the idea that the readers would have gotten would have less accurate.

Anyway, thanks for your kind attention to both my article and my book.

Sorry :(

I didn't mean to be rude, and I do recognize that any text is written keeping the target audience in mind.

I just thought that words like "concept" would be more appropriate than "data structure". No CT-awareness is neccessary, any abstract word will do, it might be even called a "gimmick". This would leave this area "gray" in readers' mind, so they would not get a false sense of confidence that they know about it - so one day they may go and explore it.

Regarding the Strong Turing Thesis - it's just my pet peeve. I never miss a chance to complain when people (mis)represent TM expressiveness as equal to that of a computer. Yes, I have heard about Wittgenstein's ladder :-)

What's the heat source ?

I don't think there's much about the interview to generate heat here on LtU. I make Anton's words mine: I agree with MJD and wish more people would think like him. I mostly emphatically agree with that:

That said, I do think that all programmers should learn as many different languages as they can, and I'm puzzled when they don't want to. It's like being a carpenter and saying that the hammer and the chisel are good enough for you, you don't need to learn to use a saw or a screwdriver.

It's not just about being functional or anything other, is being open to try and learn new tools and consider that there may be better ways to do things out there. I have often ran into trouble trying to convince programmers to at least look at other languages and try them. Some reply "I better use this time learning this or that new API for Java". It's frustrating.

Of course, but...

I remind you all that people vary in their abilities. Learning a new language is quite a hard and lengthy project for some.

I, of course, think programmers should do it anyway, and that with experience language learning becomes easier. But we should remember that some people are quite accurate in how they judge their own abilities, and act rationally when they take their abilities into account when considering which projects to undertake.

PL theory as a way off the treadmill

I have often ran into trouble trying to convince programmers to at least look at other languages and try them. Some reply "I better use this time learning this or that new API for Java". It's frustrating.

My response to this attitude is that if you invest time in studying PL and computing theory, you won't have to spend nearly as much time absorbing every new tool and API that Microsoft, Sun etc. choose to dump on us.

The API "churn" generated by the major software companies can give a convincing illusion of an extremely fast-moving field, creating the impression that it's essential to run as fast as you can to keep up — but it doesn't appear nearly so fast moving if you're able to look further ahead down the road, see where these things are coming from, and put them in a broader context.

Yes, that's what I tell my st

Yes, that's what I tell my students regularly.

They don't buy it...

Programming as Craft

Since I'm in the process of reading CTM again, I'm struck by Van Roy and Haridi's observation about programming-as-science vs. programming-as-craft. It seems to me that many programmers are doing programming-as-craft, and we are attempting to encourage them to engage in programming-as-science. But perhaps we are misguided. Perhaps, in most cases, programming-as-craft is adequate.

Hmmm. Are we back to the realization that it's fundamentally an economic question, as on the "what's the use of types" thread?

Maybe

and we are attempting to encourage them to engage in programming-as-science

That's probably true regarding most of what we do around here, the one exception is learning new languages! This is a worthy exercises even, and perhaps most importantly, if you don't practice programming-as-science (and see the "pragmatic programmer" guys for a corroborating example).

Programming as engineering

Perhaps it would be better to encourage programmers to engage in programming-as-engineering. I suggest this for two reasons:
  1. Engineering is far more focused on synthesis and design than science is. Some of the fundamental knowledge is the same, but the outlook and approach is different. David Parnas touched on this issue many years ago.
  2. A fundamental part of the engineering design process involves understanding the scope of the problem to be solved (in terms of complexity, risk-tolerance, and cost) and selecting the level of rigor appropriate to meet the design goals. A craft approach may be completely appropriate when system complexity is low and/or the tolerance for system failure is high. More rigorous methods are necessary for more complex systems.

Whether the "craft" approach is the appropriate one depends entirely on the type of design problem. You wouldn't apply the same rigor to constructing a doghouse in the backyard that you would to constructing a 100-floor office building.

If you want an economic analysis...

...you need type theory, oddly enough. For example, you can model the value of modularity in a decision-theoretic way by using the Black-Scholes equation. Roughly, modularity increases your set of options for modifying a system, and it's a basic result of options theory that having a portfolio of individual options is more valuable than having an option on a portfolio. (Intuitively, a program whose components you can selectively upgrade is more valuable than one which is a monolith which must be upgraded in a big bang.) But to use that result, it must actually be the case that your modules are modular -- and that's where you need abstraction as a semantic property. You can also use a variation on this idea to put a price on the value of static types. If your program has abstract data types (that actually work semantically), then it turns out that bisimulations of typed versions of your language are much coarser than bisimulations of the untyped versions. This means it's harder for external programs to distinguish implementations, and this means a programmer has more freedom to change a module.

A mature theory of programming would let you go from a mathematical characterization of your loss function to the structure of your program. We're a long, long way from that.

Citation?

Where did you come across this application of economics to PLT?

Check out Kevin Sullivan, Wil

Check out Kevin Sullivan, William Griswold, Yuanfang Cai, and Ben Hallen's The structure and value of modularity in software design. They're in software engineering, so they don't define modularity with the same species of formality we do, but their paper is where I learned to think of modularity in terms of real options. The stuff about the relative coarseness of typed versus untyped bisimulations I learned from Sumii and Pierce's recent POPL paper on type abstraction, which gave me an entirely new perspective on Sullivan et al's work.

APIs vs new languages.

Regarding programmers learning new languages rather than new APIs for the industrial language of their choice.

In most cases, when one is learning a new API (often in the course of their employment!), the subject matter of the API is either a) domain specific, or b) domain independent but often considered "outside the scope" of programming langauge design (things like graphics, database connectivity, middleware for interfacing with existing systems, etc.)

For these sorts of problems (and programmers), the new API is probably the more productive use of their time and intellectual capital. I like to study programming languages--but I do so strictly on my own time, as a hobby. My employer (not being in the PL or software tools business) has little use for me doing so; and I can't really argue with this point. I could argue that learning about ML makes me a better C++ programmer, but I doubt it would get me anywhere... :)

Many problems faced by professional programmers in industry are (to thoroughly and abusively overload a well-established technical term) "I/O-bound" rather than "CPU bound". By this, I don't mean that they spend most of their runtime blocked on I/O operations rather than crunching numbers; instead I mean that the complexity of such programs is found in interactions with external entities--users, databases, remote Web browsers, etc. To put it another way, many programming tasks are glue. Most of the advanced languages we advocate don't excel at these sorts of tasks (often delegating this stuff to third-party libraries or a FFI); instead they are often optimized towards "CPU-bound" tasks--those which are algorithmically complex. This dichotomy is woefully imprecise, for which I apologize...but it is one that needs to be considered. For many programmers who use Java and such for a living, learning Lisp or Haskell just doesn't provide much benefit--even if the learning could somehow come for free. More specifically, it won't help them get what their boss wants done faster. In some cases, this decision is made out of ignorance; but in many cases it's not. Haskell isn't going to make your life easier if you're job is writing EJBs or CRUD screens.

Unfortunately, too many in the PL community like to assume ignorance on the part of industrial users as the main cause of "advanced" languages failing to get greater marketshare and mindshare. Which is unfortunate.

New Glue

...many programming tasks are glue. Most of the advanced languages we advocate don't excel at these sorts of tasks...

All too true. This ought to encourage incipient PL designers, though: if you design a language that does excel at glue-ish tasks, you have a shot at popularity. This seems to be Philip Wadler's idea with Links: take some theory-coolness and apply it to the problems ordinary programmers face. I hope it works, but it's been a while since a language from academia became popular.

The glue was solved long ago...

I don't think an explosion of APIs and protocols is the solution for "glue." I think that the problem of "glue-level" interaction has a decent solution in the Unix stdin-stdout pipeline. Need interaction with a user? Take it from stdin. Need to transform some data? Pipe it through awk.

Object-oriented APIs are just too low-level for "glue"-heavy systems -- in typical CRUD development they are an abstraction looking for an application.

Even glue-friendly languages like Perl have some disadvantages compared to ksh/awk/sed/shell tools. They are not particularly declarative, and you can get bogged down in for-loops, objects, hashes, etc. and obscure the intent of the program.

Maybe a better analogy than glue is plumbing... and what is used in plumbing? Filters and pipes. :)

Pipes and filters

While the "pipes and filters" model (which has numerous names) is underappreciated these days (and certainly better for many types of concurrent systems than the multi-threaded sea-of-objects mess that is popular these days), it is in some ways orthogonal to what many APIs and other libraries do. Pipes are a transport mechanism (a largely asynchronous one), not a "language" for describing queries or requests to another system--having pipes is like having XML or RPC. It solves a class of domain-independent problems; but there's lot's of domain-specific work left to do.

Which gets back to the original point. Many of the things that industrial programmers learn is domain-specific stuff. Perhaps in the long run, it would be a better investment for them to learn more capable languages than Java or C# (a rather large set, to be sure) then to keep plugging away. However, for many, the "break even" point for such effort is years in the future; it isn't unreasonable at all to consider this a bad investment.

Domain specific vs. domain independent

If most of what programmers do is glue, then there isn't a lot of domain-specific work left to do. Glue is by definition domain-independent (e.g. "how do I get the stuff from DataSource into TransferFormat using ThirdPartyLibraries and run it through to RulesEngine so it can generate behavior for WorkflowTool?")

This is orthogonal, as you say, to the problems being solved within DataSource, ThirdPartyLibraries, RulesEngine, and WorkflowTool. But those problems aren't glue problems; they're domain-specific problems.

Perhaps we have different ideas of "glue" vs. "non-glue." To me, anything domain-specific will probably require some kind of specialized algorithm. It may or may not require a lot of heavy lifting in language abstraction, but one thing it will certainly need is an API. I claim that for most things that IT programmers do -- things that often don't require fancy linguistics, but perhaps once in a while do -- filters and pipes is more often than not the most suitable API design. Shell filters and pipes

  • often give you concurrency "for free"
  • come with the operating system
  • are more quickly composable than object-oriented APIs
  • allow for easy characterization of the inputs and outputs -- and hence the overall functionality -- of an individual component

Granted, many problems are more complicated than can be expressed directly in a shell pipeline. This is when you implement a source, sink, or filter in another language of your choice, inputting on STDIN and outputting on STDOUT.

Pypes

Pipes are a little more than that, imho. There's also this ad-hoc serialization-deserialization format, which is not necessarily published. When it fails, it fails spectacularly, but it works pretty well as long as it does.

Regarding the endless API love: It's not just the API. Realize that most companies/developers are not capable of producing quality code. Thus, they are very happy using code from Microsoft/Sun/etc. Algorithm-heavy software development is hard. Learning and mastering new languages is hard. Learning and mastering API's is not that hard since the vendor puts in a lot of effort into it.

The Languages Do Have It

Your examples, EJBs and CRUD, are actually ones where languages have been shown to be valuable IMHO. In my experience the best way to write an EJB is to not write one. Go use a language with continuations and avoid the whole mess that is Java web development. For CRUD applications, Ruby on Rails has shown that some neat metaprogramming tricks can make these systems very easy for medium sized projects. Presumably one can use the same tricks in Template Haskell, where the rules or the game are more rigidly enforced, for better or worse.

More on EJB

Regarding:

"The best way to write an EJB is not to write one".

From a theoretical standpoint, that might well be true. Java is not my favorite programming language. Being an embedded systems programmer, my EJB knowledge is limited--so I won't comment pro or con there.

OTOH, many shops have standardized--for better or worse--on EJB. (Or on numerous other competing technologies, each tied to a particular langauge or platform). If you work in such shops, EJB is effectively a functional requirement, not an architecture/implementation choice to be worked out.

And while other languages can use EJBs (especially those that will compile to Java bytecode), the combination is often less than satisfactory.

A principle that cannot be understated for programming language designers. If you want your language to be adopted, it must play nice with the rest of the world. Unless, of course, you are IBM or Microsoft (Sun to a lesser extent) and have a well-positioned platform which you can tie your langauge to. Most of the readers here (other than folks like SPJ who work at MS labs) don't have that luxury.

This is especially true in consideration of the binary-component world of today, where code fragments from different sources have to be smooshed together in the same resultant binary image (often at load time). One nice argument with the pipes-and-filters approach, of course, is that pipes don't care what language the source and sink programs are written in. But when you're loading multiple DLLs into the same process, that's a different story.

Paradigm Shift

Scott Johnson: principle that cannot be understated for programming language designers. If you want your language to be adopted, it must play nice with the rest of the world.

As true as this is, the obvious problem with it is that at some point it becomes literally progress-killing. It carries with it the implicit assumption that all necessary improvements to protocols, APIs, ABIs, libraries, language semantics, security, etc. have already been worked out and cast in stone, and that any further progress can only be incremental. When you stop for a moment to consider that digital computers have only been with us since the 1940s, it should rapidly become apparent how laughable this is.

As far as I can tell, the primary problem that computing faces is that early limitations inculcated a culture of overcommitment and premature optimization that persists to this day. Actual progress consists of reducing unnecessary coupling without introducing unacceptable costs in the process. It's far too early in the game yet to declare victory and retreat.

Cast in stone?

Paul wrote:

"As true as this is, the obvious problem with it is that at some point it becomes literally progress-killing. It carries with it the implicit assumption that all necessary improvements to protocols, APIs, ABIs, libraries, language semantics, security, etc. have already been worked out and cast in stone, and that any further progress can only be incremental."

While I sympathize and agree (in part), keep in mind it's software we are talking about. In many cases, evoluationary (rather than revolutionary) progress is possible (and when it is; I would argue that it is desirable); in the cases where an existing (and important system) is at an evolutionary dead-end, it is generally possible to encapsulate it and slowly migrate away from it.

And, many facets of the computing infrastructure are probably better left outside the scope of programming language design, anyway.

My primary objection is to systems whose premise is "the entire computing infrastructure developed over the past 50 years is garbage; abandon all that you have and come to the promised land of X" where X is an interesting (and often well-designed) system that lacks any suitable replacement for what the 50-year-old infrastructure is capable of. A certain amount of insularity is inevitable (and probably more productive) in research systems--but systems designed for production use are unacceptable if they cannot be integrated somehow into production systems--no matter how meritorious they otherwise might be.

That said, even systems that do "play nice" have a difficult time being adopted by the mainstream. One major reason for this is the business community (or that segment who purchases and/or specifies development tools) are inherently skeptical of claims of superior performance, reliability, and/or productivity--if for no other reason than the fact that decision-makers are bombarded with such claims--many of them oughtright bogus--from vendors and marketeers of all stripes. Claims that Haskell makes programmers more productive than Java--even if well-documented--are often met with "yeah, sure it does". Scientific evidence isn't a very effective argument, unfortunately, as many decision-makers don't read scientific literature (or their idea of a scientific journal is ComputerWorld), and many vendors are quite good at writing marketing literature that looks like scholarship, and getting it published.

Unfortunately, we in the PLT community who advocated such advanced languages have a difficult sales job in front of us. It is far too easy to become discouraged, bitter, or cynical when we build a whole boxful of better mousetraps and the world doesn't beat a path to our door.

...these things we call Progress....

Targeting the Windows environment for the tools ignores the fact that Microsoft is trying their best to supplant COM/Active-X (or whatever they call it this week) with the .Net framework. So these current environs couldn't be too good, or they wouldn't need to be replaced. Anyhow, it's a moving target.

And to carry on the rant to dangerous territory, EJB must've been designed by a bunch of ex-RPG specialists who figured that we all needed to harken back to the days of cycle programming.

Agreed

I'm always happy when a language community adopts new (for them) concepts. I was happy when C++ got more functional, and I'm happy if Perl gets more monadic. :-)

I certainly feel the same way that the quote indicates and share Andrei's frustration with what often seem to be self-imposed limitations on learning. Learning the concepts is far more helpful than just learning the language and its idioms, but it's very difficult to convince people of that.