Settings

Theme

The Lisp Curse (2017)

winestockwebdesign.com

64 points by gphilip 4 years ago · 92 comments (91 loaded)

Reader

at_a_remove 4 years ago

The results (many many packages doing fifty to eighty percent of what you need) are what drove me from Perl and what makes me very uncomfortable with the growing disdain for the standard library in Python. I really don't want to write my own XML libraries or whatever, I would rather just import whatever the standard solution is. I also do not want to have to do a roundup of the available solutions and try to figure out which is most applicable, then hope that it will actually do the job.

A lot of people are very into whatever the language is, but for me, I want a huge standard library.

badsectoracula 4 years ago

> Making Scheme object-oriented is a sophomore homework assignment. On the other hand, adding object orientation to C requires the programming chops of Bjarne Stroustrup.

C++ added a ton of additional stuff to C. The original Objective-C is a much simpler approach on adding object orientation to C and at its core it'd all be about finding expressions like

    [foo bar:baz boo:hoo]
and replacing them with something like

    obj_send(foo, msg_foobarboo, baz, hoo);
and linking with an underlying runtime that handles message passing of course.

An alternative would be Turbo Pascal 5.5-style OOP where

    struct foo : base {
        foo();
        ~foo();
        void blah();
    }
    foo::foo(){ base(); }
    foo::~foo(){ ~base(); }
    void foo::blah(){}
would be accepted but aside from the C++-like syntax for constructors, destructors (which handle the hidden VMT field) and methods nothing is done automatically and instead you are expected to explicitly construct and destroy the objects (if needed), e.g.

   struct foo foo;
   foo.foo(); /* call constructor chain */
   foo.~foo(); /* call destructor chain */
or

   struct foo* foo = malloc(sizeof(struct foo));
   foo->foo(); /* call constructor chain */
   foo->~foo(); /* call destructor chain */
   free(foo);
Note that Objective-C handles (or handled at the past, not sure how things changed nowadays) allocation and construction in separate steps too.

Of course unlike a language with Lisp-like macros you'd need to modify a compiler or write a preprocessor to do the above, which makes it a bit harder, but in any case adding object orientation to C does not mean you have to make it as complex as C++.

  • xscott 4 years ago

    Yeah, I agree. If you're willing to use a garbage collection library [0], you can even have a pleasant syntax for ObjectiveC style OOP in C:

        var result = call(foo, "bar: %s boo: %f", baz, hoo);
    
    The garbage collector will pick up the stray memory and release other resources (files) as needed, and all the standard compilers will check the varargs format string for you.

    Dynamic typing, arbitrary messages, and no memory leaks. Just like Lisp. It's not perfect (string message could have typos, and might use %p for objects), but it's not too bad.

    [0] https://en.wikipedia.org/wiki/Boehm_garbage_collector

    • lisper 4 years ago

      Why do you need GC to support this syntax? The syntax has nothing to do with whether or not the semantics of the language permit memory leaks.

      • xscott 4 years ago

        You don't need the GC of course, but manually tracking and releasing the memory takes all the fun out of this kind of high level programming, particularly when you start to nest expressions. As a hypothetical example:

            call(
                window, "draw: %d %d %p", x, y, 
                alloc("Circle radius: %d color: %u", r, 0xFF0000)
            );
        
        That ignores the return value and loses track of the temporary argument.

        This is all in response to the article claiming you "need to be Bjarne Stroustrup to add OOP to C, but it's a sophomore assignment to add it to Lisp". If I hadn't mentioned the GC, someone else would've jumped on the example for how unpleasant manual memory management is in comparison to Lisp.

        • lisper 4 years ago

          I was responding to this:

          > If you're willing to use a garbage collection library [0], you can even have a pleasant syntax for ObjectiveC style OOP in C:

          That sounded to me as if you were claiming that GC is a pre-requisite for having a particular syntax. But I gather that's not what you meant. I'm still a little unclear about what you actually meant. You can have memory leaks like the one in your example above in vanilla C without any OOP features at all. GC is completely orthogonal to OOP, and both are completely orthogonal to syntax.

          • xscott 4 years ago

            Yeah, I got your point. I don't think we're in disagreement about anything, and I probably shouldn't have conflated multiple topics. It's not really _syntax_, but this would be uglier to me:

                var temp = alloc("Circle radius: %d color: %u", r, 0xFF0000);
                var ignored = call(window, "draw: %d %d %p", x, y, temp);
                drop(ignored);
                drop(temp);
            
            What's a good word for the overall/high level result being less attractive while the low level syntax isn't really the problem? Having a GC does tidy up the code and make it feel high level like Lisp/SmallTalk.
            • lisper 4 years ago

              I don't know of a word for it. It's just a fact: GC simplifies code because it liberates the programmer from having to figure out when memory can be safely reused and transfers that responsibility to the runtime. It has next to nothing to do with any other aspect of language design, except insofar as if you have GC then your language can get by without any mechanism to allow the programmer to free allocated memory. This observation has some pretty significant practical impact, but you can't say much more about it than that.

  • edgyquant 4 years ago

    What’s the point of a constructor that isn’t called immediately? Couldn’t you just use any arbitrary function at that point?

    • badsectoracula 4 years ago

      If a constructor is called automatically then it also needs the destructor to be called automatically and both introduce a bunch of additional complexity, especially for stack allocated functions, the need to take into account the concept of a default constructor (not necessarily requiring it but still needing to consider it), etc so that someone doing...

          while (something) {
              foo foos[42];
              /* use foos here */
          }
      
      ...will still have their 42 foo constructors and destructors called at the appropriate times.

      Meanwhile by doing it manually you just bypass all that complexity at the language level and it becomes the programmer's responsibility to do it (or not) properly.

      Also while you often want the above, this isn't something you always want, e.g. when you need to differentiate between where the memory of "foo" comes from and its lifecycle as an object (e.g. custom memory allocators, reusing objects without allocating/releasing their memory, etc).

      Of course all the above could be done with functions too, after all there are a bunch of C programs and libraries doing OOP without the language itself providing any support for it.

arethuza 4 years ago

"The hardest problem in computer science is not being an opinionated jerk about everything."

From the author's home page.

Edit: Potentially ignoring that quote - I can't help observing that although I used Common Lisp as my main development language for 6 years in an academic research environment and really enjoyed it I've never wanted to use it since then...

rileyphone 4 years ago

I would argue that rather than some curse of expressiveness, the lackluster showing from the community in recent years has been the results of a premature standards process. Common Lisp hasn't changed since before I was born, and while to some people that denotes stability, it also leaves new features to be done in the manner the author describes, as 80% projects by lone hackers. The language is more than capable of supporting modern development, but simply requires learning too much context and historical baggage to be appealing to any but the most devoted. This has little to do with expressivity, but more with history and economics. Most successful languages have one or more companies devoting resources to the language and libraries. Lisp has multiple implementations of the language but no blessed one, which means the fossilized standards are the point of departure for each of them, many remnants of the era of software you can buy.

There are still a lot of interesting things happening with Lisp, but I can't see how Common Lisp will be the path forward. Of course, there have been many challengers seeking to upset it as King Lisp, including this site's very own Arc. Clojure has seen the most commercial success in recent years, though the extent that it's actually a Lisp is debatable. I'm a fan of Kernel [0], which makes macros first class members of the language, like everything else. Who knows, but saying it's power will necessarily lead to its downfall is a kind of fatalistic mentality that I have little patience for.

[0] https://web.cs.wpi.edu/%7Ejshutt/kernel.html

johnisgood 4 years ago

> Dr. Mark Tarver — twice-quoted, above — wrote a dialect of Lisp called Qi. It is less than ten thousand lines of macros running atop Clisp. It implements most of the unique features of Haskell and OCaml. In some respects, Qi surpasses them. For instance, Qi's type inferencing engine is Turing complete. In a world where teams of talented academics were needed to write Haskell, one man, Dr. Tarver wrote Qi all by his lonesome.

Check out https://github.com/factor/factor. Check out how much stuff they have implemented early on, just 2-4 guys tops. I found it really impressive.

toolslive 4 years ago

> Employers much prefer that workers be fungible, rather than maximally productive.

  • lisper 4 years ago

    This. A maximally productive non-fungible employee has leverage, and employers hate that more than just about anything.

davidgrenier 4 years ago

I just wish more people understood that something being Turing Complete isn't a feature, it's a flaw.

  • lisper 4 years ago

    Turing completeness may be a flaw, but it is nearly impossible to avoid.

    • gnulinux 4 years ago

      Not true at all. It is hard, but not impossible. Technologically it's very challenging because we don't have non-TC programming languages that are able to keep up with modern ones. But, for example, we have (safe) Agda which is not TC (all programs marked --safe should prove to halt) and you can write useful programs. Here, "useful" is a subjective qualifier, but I personally implemented many parsers in Agda (including a json parser) so for my definition of useful, Agda is one such language.

      • lisper 4 years ago

        I didn't say it was impossible. I said it was nearly impossible, which is a synonym for "hard" for some value of hard.

        Case in point: I looked into Agda and ended up in a deep rabbit hole that involved something I had never heard of called "Walther recursion." Whether this qualifies as "nearly impossible" or merely "hard" is quibbling over terminology, not substance.

  • tharne 4 years ago

    How so?

    • gnulinux 4 years ago

      E.g. you can require all programs to halt, which makes the language non-TC since the language has a trivial solution to its halting problem. There are other ways too, but this is approach e.g. Agda takes.

      Note that you can still build useful programs this way since such languages can still allow certain forms of recursion such as primitive recursion, structural recursion etc... You can also use sized types [1] to allow even a larger set of (halting) programs.

      [1] This is a way of compiler statically analyzing the size of each type (i.e. how many recursive constructors necessary) which puts an upper bound on the number of recursions need to be performed.

    • mvaliente2001 4 years ago

      If your type system or log formatter is turing-complete, it can be exploited to do arbitrary unintended things.

    • davidgrenier 4 years ago

      Also, Turing Completeness is almost always accidental while non-TC is obtained by design. Hence, just about anything has Turing Completness which doesn't make it a feature.

      Now if you want to gain the ability to make serious proofs about your programs, one can make the argument you need non-TC.

    • eimrine 4 years ago

      Maybe the previous speaker means the "tragedy of Common Lisp", where (in my understanding of the problem) it was happened to became too much of clever developers which decided to add too much of clever things in main library which are required to be known for keep writing the compiler in same code style (I am not a real programmer but have a sympathy to that answer, please correct me for creating more precise answer).

ashton314 4 years ago

Mathematicians and physicists would rather use another's toothbrush than another's notation.

Perhaps The Curse is because Lisp programmers are generally of the same ilk as mathematicians and physicists?

Flankk 4 years ago

> Real Hackers have also known, for a while, that C and C++ are not appropriate for most programs that don't need to do arbitrary bit-fiddling.

Strongly disagree with this statement. I've read it so many places now that it has to be a meme. I actually wish I could use C++ on the web instead of this JS nightmare ecosystem. I don't understand where the idea comes from. I'm never "bit-fiddling" in C++ and almost never need to use pointers.

  • klibertp 4 years ago

    In my experience the best for "bit-fiddling" is Erlang (and, by extension, Elixir) which offers bit-string literals[1], along with pattern matching on them. It's trivial to implement any binary protocol or parse any binary file format with these. It makes bit-fiddling pleasant and fun, but nobody ever mentions Erlang in these discussions.

    That's because most programmers are incapable of making any informed decision about the language they use (and, even more so, about languages they don't use). There's a strong tribal mentality, a lot of cargo-cults, and the very narrow perspective on what's possible and (more importantly) what's desirable is prevalent.

    [1] https://www.erlang.org/doc/programming_examples/bit_syntax.h...

    • lisper 4 years ago

      Common Lisp has bit string literals:

          Welcome to Clozure Common Lisp Version 1.11-r16812M  (DarwinX8664)!
          
          ? #*010010010101001
          #*010010010101001
          ? (type-of *)
          (SIMPLE-BIT-VECTOR 15)
      • klibertp 4 years ago

        I think it's not unusual to have base-x number literals (even Python got `0b01101` literals at some point), but not many languages support pattern matching on bitstrings. In Erlang, it looks like this:

            1> A = 2#0010010010101001.
            9385
            2> << _:2, B:4, _/bitstring >> = << A:16 >>, B.
            9
            3> io:format("~.2B~n", [B]).
            1001
        
        I put your number into 16-bit bitstring[1], then ignored first 2 bits, extracted the next 4 bits, and ignored the rest.

        CL doesn't have pattern matching in the standard, IIRC, but there are libraries implementing it, so I wouldn't be surprised if one of them also offered bitstring matching, but that's beside the point: I'm comparing Erlang and C++ here, not Erlang and CL.

        [1] It could be 14 or 15 bits, but I wanted to have a bit of a leading padding to ignore in the pattern.

        EDIT: I missed the fact that the #*01... literal in CL is not a number, my bad. The equivalent literal would be << 2#01...:N >> in Erlang, but you need to give the N (number of bits) yourself, so it's a bit less convenient.

  • bayesian_horse 4 years ago

    Whoever says things like that probably means "appropriate" in the sense that you can get your stuff done with another language using a fraction of the implementation time.

    And whoever wishes to use C++ on websites... who is stopping you since Webassembly? Speaking about ecosystems... I also don't think the package management ecosystem in C++ is that much better, right? And there are enough horror stories about illegibility and foot-guns even in modern C++ code, rivaling the worst YOLO frontend style...

    C++ requires you to be a lot more verbose and precise for almost everything. That translates to more work, and the benefit isn't automatically worth anything.

    • Flankk 4 years ago

      Wasm is bleeding edge. AFAIK the only compatible UI library is Qt and support is not production ready. I have never needed package management in C++. There are gotchas with all languages, Lisp is not a panacea. Language verbosity is not bad it's a tradeoff, functional languages are usually hard to read. The language requiring you to be precise is a good thing. There's a reason the web industry has moved to TypeScript.

      • bayesian_horse 4 years ago

        Wasm is not just bleeding edge, it is supported by all major browsers and being used in all sorts of real-world websites. No, "Qt" is not the only way to do UI in C++/wasm. This is a basic misunderstanding of the technology. Wasm lives inside the Javascript vm and can manipulate DOM objects all day long. It's just not very practical to do so. There are plenty of Rust projects going in that direction, though...

        C++ doesn't only require you to be precise, it requires you to be verbose. JS is quite precise, and a lot more expressive because of the runtime. TypeScript is all of this and also allows you to be more explicit in order for the compiler to check your work, much like a proof checker.

        The C++ type system is relatively stupid compared to that of TypeScript and F#, for example. In TS and F#, you can use types to help you, in C++ you already need the types because otherwise the compiler doesn't have a clue what to do.

  • mtreis86 4 years ago

    On the opposite end, Common Lisp is actually pretty decent for bit twiddling. It has the operators from the PDP instruction set, LDB and DPB, which load and deposit bytes of varying length from and into other numbers.

  • scns 4 years ago
  • vaylian 4 years ago

    Webassembly might be the solution to your problem

    • Flankk 4 years ago

      On the frontend. In a number of years. It's in its infancy. Instead of hacking a webpage to behave like software it actually will be software. So I'm pretty excited about the idea.

  • dkersten 4 years ago

    I like working in C++, after a decade of working in Java, Python, Javascript and Clojure, I find working in C++ (which I learned before these other languages) to be quite fun and pleasant, at least with relatively modern C++.

    I've been, on and off, working on a little toy game engine, for a few years. Its a mix of keeping up with C++ advancements, learning various concepts like physically based rendering, and just the fun of crafting a big project, with no constraints other than my time and ability, no deadlines, no expectation of releasing anything. Its cathartic and enjoyable. I really do enjoy it.

    Last September, I got frustrated with something I was working on in a more serious capacity. It was some server software, it responded to HTTP requests, it accessed third party services over HTTP and Websockets, it talked to a Postgres database. Overall it was an event driven system that transformed data and generated actions that would be applied by talking to third party services. The "real" version was written in Clojure and it worked pretty well. I really like Clojure, so all good.

    But because I was frustrated with some things about how it ran and the resources it took up, I wondered what it would be like if I developed a little lean-and-mean version in C++. So I gave it a try as a side project for a few weeks. I used doctest[1] for testing, immer[2] for Clojure-like immutable data structures, [3] lager for Elm-like application state and logic management, Crow[4] for my HTTP server, ASIO[5] and websocketpp[6] for Websockets, cpp-httplib[7] as a HTTP client and PGFE[8] for Postgres, amongst some other little utility libraries. I also wrote it in a Literate Programming style using Entangled[9], which helped me keep everything well documented and explained.

    For the most part, it worked pretty well. Using immer and lager helped keep the logic safe and to the point. The application started and ran very quickly and used very little cpu or memory. However, as the complexity grew, especially when using template heavy libraries like lager, or dealing with complex things like ASIO, it became very frustrating to deal with errors. Template errors even on clang became incomprehensible and segmentation faults when something wasn't quite right became pretty hard to diagnose. I had neither of these problems working on my game engine, but both became issues on this experiment. After a few weeks, I gave up on it. I do think I could have made it work and definitely could go back and simplify some of the decisions I made to make it more manageable, but ultimately, it was more work than I had free time to dedicate to it.

    So my experience was that, yes, you can write high level application logic for HTTP web backends in C++. You can even use tools like immer or lager to make it feel very functional-programming in style and make the application logic really clean. Its not hard to make it run efficiently both in terms of running time and memory usage, certainly when comparing to Clojure or Python. However, I found that over all, it just wasn't as easy or productive as either of those languages and I spent more time fighting the language deficiencies, even with modern C++, than I do when using Clojure or Python.

    I think I would think very long and hard before seriously considering writing a web backend in C++. If I had the time, I'd love to retry the experiment but using Rust, to see how it compares.

    [1] https://github.com/doctest/doctest

    [2] https://github.com/arximboldi/immer

    [3] https://github.com/arximboldi/lager

    [4] https://github.com/CrowCpp/crow

    [5] https://think-async.com/Asio/

    [6] https://www.zaphoyd.com/projects/websocketpp/

    [7] https://github.com/yhirose/cpp-httplib

    [8] https://github.com/dmitigr/pgfe

    [9] https://entangled.github.io/

rurban 4 years ago

nit: it's (2011) not (2017)

otherwise, he speaks from my heart. social issues only

adregan 4 years ago

OP posted despite the opening paragraph!

> Update on October 6, 2017. N.B.: Please stop submitting this to Hacker News! Look at the Hacker News search results for this essay. Check out the note for the first entry: Come on, everyone! Let's beat the dead horse one more time!

Past discussions https://hn.algolia.com/?query=The%20Lisp%20Curse&type=story&...

  • badsectoracula 4 years ago

    AFAIK it is common to repost a story here if there has been enough time since the last post since there can be new voices, opinions, etc since the last time it was posted. Dang sometimes posts a comment with links to previous discussions too.

    Perhaps the author is confusing the norms with Reddit where in many subreddits reposts are often frowned upon.

    • cogman10 4 years ago

      So long as the year is clearly stated, I do think reposts are a bad idea on HN.

      There have been plenty of old articles that I've seen for the first time in a repost.

  • iamwil 4 years ago

    Dunno, I've been on HN since 2007 and this is the first time I've seen this story.

    • vaylian 4 years ago

      Yes. XKCD 1053 applies here. And this is evergreen content.

      I wonder why the author is upset about the posts. Does it generate too much costly traffic? Do they receive a lot of e-mail because of their essay?

  • usefulcat 4 years ago

    shrug. The way things work is people upvote things because they find them interesting. If enough people hadn't upvoted it, it would never have showed up on the front page, and most people probably wouldn't have seen it. Anyway, I'm not sure why they care that it gets resubmitted..

  • coldtea 4 years ago

    That's a plea from 5 years ago.

    People resubmit stories all the time, new and better (or different) discussions form around each resubmission, and new people get to read it.

_hcuq 4 years ago

If Lisp is do efficient for development, why are there essentially no commercial products that use it?

  • hajile 4 years ago

    StandardML vs go is a great illustration.

    StandardML is just as fast, is more simple to learn with more simple syntax and basically zero gotchas, has more powerful syntax, has an actually sound type system (which has better generics than the ones proposed in go), does a better job at defining public functionality (via modules), has a better CST model, and many other great features.

    The only area where it loses is standard libraries and marketing. Google invested millions into these two things, so people use their decidedly inferior language.

    You'll find that pretty much every big language has a big company behind it that threw tons of money at its development.

    • zelphirkalt 4 years ago

      I am learning SML currently (with the book "Elements of ML Programming" by Jeffrey D. Ullman) and I have to say it is quite elegant. I like the pattern matching for functions. Often it is surprising how much shorter functions become, when you pattern match in the signature of the function. Makes me think, that maybe I should think about using pattern matching more in Scheme as well. And that I don't want to miss it in any new language I learn. Of course also the type safety is great. I could imagine writing critical parts of a system using SML.

    • TurboHaskal 4 years ago

      Do you know how good SML's concurrency story is these days?

      I tried http://mlton.org/ConcurrentML but gave up due to lack of time and the state of the documentation.

    • nonameiguess 4 years ago

      SML is great as a language, but has terrible tooling and a balkanized ecosystem of incompatible implementations, many of which only support REPL workflows (and these tend to be the implementations used for teaching). These are a far cry from the typical "point a compiler at a build file and go" that developers are used to. Go may be a strictly worse language as a language but still be better for building and distributing applications. SML is also very poorly documented, and it is rarely clear which implementation's documentation you're even reading when you find something on the web, which can often lead to quite a bit of frustration. Go, on the other hand, is extremely well-documented.

      • hajile 4 years ago

        SML doesn't have "incompatible" implementations per-se. If you stick with what the standardized language and basis libraries specify, your code will compile everywhere (I don't know of any popular implementation that doesn't support the spec). If you use their proprietary extra features, then portability will naturally go down.

        The primary means of developing uses SML/NJ for development and MLton for the final, optimized build. Both use the same Compilation Manager[0] and generally share the same ecosystem so using them together pretty much just works.

        [0] https://www.smlnj.org/doc/CM/new.pdf

      • BeetleB 4 years ago

        Your parent acknowledged everything you said in his comment.

  • jcranmer 4 years ago

    The usual answer here, as several of my sibling comments have pointed out, is that popularity and quality are not necessarily correlated. Since this has already been discussed, I won't delve further.

    Another answer that hasn't been discussed much is that... maybe it isn't better for development. The article discusses one way in which this could be true: that technical superiority essentially leads to a hopeless community fragmentation that more or less forces it to be inferior in terms of community effects (which are, presumably, more important for commercial development rather than individual development).

    A different facet, though, is that I believe the better language isn't the one that gives you more powerful tools to write correct code, but the one that keeps you from writing incorrect code (while still letting you write correct code). A salient example here is goto. Most modern languages don't have the goto keyword anymore, but they instead retain things like break, continue, and early routine... all of which are restricted forms of goto. By using only these restricted forms instead of the general form, it is much easier to immediately see what the code is doing (and presumably quicker to understand why), even though it may strictly be less powerful.

  • tharne 4 years ago

    > If Lisp is do efficient for development, why are there essentially no commercial products that use it?

    Same reason most of us use QWERTY keyboards instead of one the many better layouts available. After a long enough time as the dominant tool, things get locked in regardless of whether or not they're the best tool for the job. C-Style languages gained dominance early on and became the defacto standard.

    • Syzygies 4 years ago

      > Same reason most of us use QWERTY keyboards instead of one the many better layouts available.

      Many people here are coders, not writers, and the layout for generating human language is irrelevant. With QMK firmware tap-hold, and one finger each hand chording, one opens up a quadratic expansion of expressibility, all near home row. Now one can automate all frequent actions (VSCode commands, application launches, windowing scripts) as paired keystrokes.

      Keyboard layouts should be the poster child for "Don't get sucked into taking the problem statement as given, THAT's usually what needs questioning."

      • tharne 4 years ago

        > With QMK firmware tap-hold, and one finger each hand chording, one opens up a quadratic expansion of expressibility, all near home row.

        I'm a happy qmk enthusiast. My point was that the overwhelming majority of people will stick with the defaults for most things, which is why usage and adoption rates are not always a good indicator of the quality or utility of a tool.

  • throwaway599281 4 years ago

    This week there was the annual European Lisp Symposium [0], in Porto, Portugal, and it's sponsored by companies who use Lisp in their products.

    If you have ever taken a train or subway in Europe, you depended on Lisp.

    [0] https://www.european-lisp-symposium.org/2022/index.html

  • a4isms 4 years ago

    > If Lisp is [so] efficient for development, why are there essentially no commercial products that use it?

    I’m sorry you’ve been downvoted for asking this question, even if it was a rhetorical question.

    It’s easily the most important question to ask in the professional programming area, and it’s worth the effort to truly grok the answers rather than look up what everyone seems to say and then repeat it as gospel.

    It may be asked and answered ad nauseam, bit it’s worth answering in the context of the very article discussing the Lisp curse.

    Read TFA. What if every programmer rolling their own version of everything makes it an astoundingly good language for people but terrible for gaining industry-wide adoption?

    JavaScript had this problem with every framework implementing its own OOP. Ember.js comes to mind as a recent example. The language stewards added a class keyword to ES6 in large part to quash further Balkanization of JS OOP.

    Why didn’t JS wither while Lisp did? Ah! The answer is very relevant to your question. Every popular language began as the scripting language for an explosively successful platform.

    JavaScript being the only way to script browsers bought it over a decade of time to fix its warts while it really wasn’t a “good” general-purpose language strictly on its merits.

    Likewise, C and C++ were the scripting languages of Unix and Windows native application development. Ruby is the scripting language of Rails, for another example.

    What is Lisp the scripting language of? A CS wag would reply, “Lisp!” And that is simply not good enough to motivate enough people to standardize the things that would lead to widespread adoption.

    It’s a social problem, just as TFA says. Which leads us to a different essay about Lisp succeeding and failing:

    https://en.wikipedia.org/wiki/Worse_is_better

    • lispm 4 years ago

      Lisp was the main language of Symbolic AI. That market largely crashed in the 80s/90s.

      Planners&scheduling in the military&logistics (airlines, airports, train operators, satellites, ...), expert systems for maintenance, computational engineering systems (for example for airplanes from Airbus and Boeing), theorem provers (used in chip design), symbolic mathematics, natural language systems (text translation for the EU), ...

  • leobg 4 years ago

    Alan Kay‘s answer to this question:

    “Another interesting answer assumed that “the test of time” is somehow a cosmic optimization. But as every biologist knows, Darwinian processes “find fits” to an environment, and if the environment is lacking, then the fits will be lacking. Similarly, if most computer people lack understanding and knowledge, then what they will select will also be lacking. There is abundant evidence today that this is just what has happened.”

  • davidgrenier 4 years ago

    The answer is always that popularity doesn't correlate with merit.

    • tharne 4 years ago

      > The answer is always that popularity doesn't correlate with merit.

      Exactly. If we used popularity and usage rates as the measure of merit, we'd have to conclude that the highest quality restaurant in the world is MacDonald's.

      • eimrine 4 years ago

        > the highest quality restaurant in the world is MacDonald's.

        Isn't it so? The meal is enough healthy (for hard-workers only, not for calories-gathers), calorage as I have mentioned is excellent, waiting is minimum, non-meal payings (keeping the restaurant attractive) are the lowest possible, the most important thing is that in poor countries (my is in the bottom of bigmac index) the prices are lower than anything else available in big cities.

        • BeetleB 4 years ago

          I'm one of those who actually likes McDonald's burgers. However, in the last year I decided to stop going there because of multiple experiences with restaurants near me where I ordered to go, and parts of the burger were cold. As in fridge cold.

          As for price - not sure what you mean by "poor" countries. In the ones I've traveled to, McDonald's is considered a high end restaurant and is not cheap by the local standards.

        • paperclipp 4 years ago

          >The meal is enough healthy Have you been sleeping under a rock for the last 20 years ? McDo food has never been healthy. The nutrient content is poor, potatoes are cultivated with nasty insecticides, shit in the meat, etc, etc

          • eimrine 4 years ago

            > McDo food has never been healthy

            What do you think is needed to be add or to be removed?

            > The nutrient content is poor

            Can you disclosure your information a little bit? Maybe you have a link to some publications or anything better then just an opinion.

            > potatoes are cultivated with nasty insecticides

            Of course they are, or you know any better protection from colorado beatle? If you are living in America or in another place where transportated species are not a problem for your local nature - you can not even imagine what a hard problem is to beat a specie which has no nature enemies.

            > shit in the meat, etc, etc Well, I don't know where to get better ingredients then MacDo has gotten. I definitely not sure that meat in my fridge has no shit tbh.

      • scns 4 years ago

        High quality ingridients are costly too.

  • TurboHaskal 4 years ago

    For the same reason we are using VHS and have JavaScript running in the browser.

  • 83457 4 years ago

    With Clojure out there now I think the number of products using a Lisp is underestimated.

    • eadmund 4 years ago

      But Clojure is not a Lisp. It is Lisp-adjacent, a bit, but it is really not the same language.

      • throwaway599281 4 years ago

        >Clojure is a dialect of Lisp, and shares with Lisp the code-as-data philosophy and a powerful macro system. [0]

        Neither the Clojure page, nor its users seem to agree with you.

        [0] https://clojure.org/

        • remexre 4 years ago

          I think the typical argument goes something along the lines of, "it uses []{} and doesn't make cons the default data structure, abandoning some simplicity-of-language."

        • nerdponx 4 years ago

          It's not Lisp-as-in-Common-Lisp. It's closer to Scheme than to CL.

          But it's "a Lisp" in the colloquial sense that it uses s-expression syntax and has macros.

          • lispm 4 years ago

            Not s-expressions in the traditional Lisp definition of singly linked lists. In Lisp (a . b) is a cons cell with two symbols a and b. In Clojure it is some complex data structure with three elements a, ., and b.

      • speed_spread 4 years ago

        Let's see:

        - Insists on every expression being (wrapped (in parenthesis))

        - Uses polish prefix notation

        - Profound belief that recursion is more intuitive than loops

        - Macros everywhere, because code is data, so why not?

        - Whole language built from a very small set of axioms

        - REPL-based workflow

        QED Clojure is _a_ Lisp.

        (FWIW I'm learning Racket right now)

        • jhgb 4 years ago

          Lisp: "List processing". Clojure doesn't even have cons cells... A Lisp without cons cells is like a C derivative without pointers...is it really C at that point? I'd also question the "profound belief that recursion is more intuitive than loops" since Lisp supports loops extremely well -- better than most languages, since you can build up your own iterative constructs using tagbody. And Clojure doesn't even have proper tail calls, so I doubt that Clojure actually believes in recursion.

          • speed_spread 4 years ago

            Clojure doesn't have tail calls because they should be implemented at the JVM level to be effective, a feature which has been on the back burner for ever because no other languages would use them.

            • lispm 4 years ago

              Programming languages on top of the JVM would not use that? Who said that?

      • bigbillheck 4 years ago

        Perfect example of the Curse, thank you.

Keyboard Shortcuts

j
Next item
k
Previous item
o / Enter
Open selected item
?
Show this help
Esc
Close modal / clear selection