Live data from Hacker News

How to write Common Lisp in 2017 – an initiation manual

articulate-lisp.com

41–50 of 271 posts

Re: How to write Common Lisp in 2017 – an initiation manual

#41

Earlier quoted context omitted.

I'll take a stab at this glib comment: 1. You've inherited an application written in Common Lisp 2. Common Lisp has features you find desirable that aren't available in another system 3. You like Common Lisp 4. Common Lisp helps you get the thing you're trying to do, done

1. Because I was forced to? That's not why I'd want to. 2. Examples? 3. Fair enough. Though AlexCoventry's question probably shows that he does not (currently) like Common Lisp, so this answer doesn't give him a reason. 4. Sure, that's true for every language and tool. Choose it when it helps you, don't when it doesn't. But why would CL help me more than another language?

> 1. Because I was forced to? That's not why I'd want to.

You might find it pleasant. Who knows? Maybe you're a professional and you'd want to understand CL so that you can embrace and extend the system you've inherited.

> Examples?

Conditions and restarts. Incremental compilation. CLOS. Numerics.

> 4. Sure, that's true for every language and tool. Choose it when it helps you, don't when it doesn't. But why would CL help me more than another language?

CL is more like a system than a compile-and-run language. The compiler, debugger, standard library, and platform libraries all live in the image. You build the program as you go, incrementally, and can inspect it while it is running.

An error doesn't halt the entire process... instead condition handlers can either choose a restart (including asking the user what to do) and the execution continues. That's where you can attach to a remote image running on a server, notice that there's an error with a particular request, inspect the entire stack, fix the problem, and continue the request. No need to crash or anything like that. If a more hands-off approach is necessary then a handler can be written to choose an appropriate restart.

CLOS is great. You can change the class definition in a running image and the instances will incrementally update without recompiling and restarting the program (and rebuilding all of that state).

You can develop the language you need with these tools instead of using the language you've chosen (or inherited). Need an interactive prover? Try ACL2. Experimenting with sequent calculus? Want a language built around recursive fractals?

Re: How to write Common Lisp in 2017 – an initiation manual

#42

Earlier quoted context omitted.

I'll take a stab at this glib comment: 1. You've inherited an application written in Common Lisp 2. Common Lisp has features you find desirable that aren't available in another system 3. You like Common Lisp 4. Common Lisp helps you get the thing you're trying to do, done

1. Because I was forced to? That's not why I'd want to. 2. Examples? 3. Fair enough. Though AlexCoventry's question probably shows that he does not (currently) like Common Lisp, so this answer doesn't give him a reason. 4. Sure, that's true for every language and tool. Choose it when it helps you, don't when it doesn't. But why would CL help me more than another language?

To 2 and 4.

Better exception handling (conditions and restarts), advanced OOP capabilities, proper macros which are convenient to use (pretty much requires a language to be homoiconic), image-based development with ability to hot-swap any code in a running program, including but not limited to full class redefinitions without losing data. All that with resulting code able to achieve close-to-C++ performance thanks to very good (commercial and open-source) compilers. Not to mention the stability of the language thanks to the ANSI standard.

Re: How to write Common Lisp in 2017 – an initiation manual

#44

I'm used to languages like Python, that have a number of files that are modules, and to start a program you run one of them as an entry point. C programs consist of a lot of files that are compiled and linked into a binary executable. Whenever I've tried to learn CL, I couldn't really wrap my head around what the eventual program would be. You build an in-memory state by adding things to it, later dump it to a binary…

In a compiled system like SBCL, things work much as they do in C, except the process is more "programmable."

To recap: when you load a (dynamically-linked) C program in Linux or OS X, the OS will create a new process, and map the dynamic linker (ld-linux.so or dyld) into that process's memory. It then transfers control to the dynamic linker. The dynamic linker then loads the rest of the program into memory (from ".so" or ".dylib" or ".dll" files) and links everything together (i.e. resolves symbol addresses) before passing control to the application entry point.

A compiled Lisp system like SBCL works much the same way, except it uses its own linking/compilation machinery. A new process is bootstrapped by running a C program, which loads the Lisp image into memory. The image is compiled code/data containing the Lisp runtime, compiler, and standard library. After the Lisp image is loaded, you've got two things to work with: COMPILE and LOAD. COMPILE takes Lisp source code and compiles it into a FASL (compiled code and data, equivalent to a ".o" file). LOAD functions much like dyld or ld-linux, and loads compiled code and data into the running process. Indeed, in some implementations like ECL, LOAD is just built on dlopen(). The "eventual program" is ultimately built by LOAD-ing the FASL files comprising the program.

In practice, you don't do this manually. Instead, you use something like ASDF: https://common-lisp.net/project/asdf/asdf.html#Defining-syst.... ASDF functions much like 'make' in that you've got a system definition listing the files belonging to your program. Whenever you call ASDF from the REPL, it'll look at what source files need to be (re)-built, compile them to FASLs, and (re)-load them into the running process. In contrast with C (but similarly to Python), Lisp allows code to be loaded into a running image. In the Lisp workflow, you don't restart the program you're writing each time you recompile (although you can, if you want). Instead, you keep it running, and load or re-load code into it as you work on it.

Re: How to write Common Lisp in 2017 – an initiation manual

#45
post #8

Earlier quoted context omitted.

Nope, it has new problems that are (IMO) worse.

I have dabbled in Common Lisp over the years and am quite comfortable with it. I know nothing about Clojure. What are the problems with Clojure? I am just curious. Thanks!

If you know Common Lisp reasonably, you'll probably have some insight into Clojure, e.g. Leiningen is a system definition facility; seq is an extension of sequences; and multimethods are generics much like methods. I'd say Clojure stands on the shoulders of giants.

There are some Lispy things that Clojure does out of the box that are more Lispy than than Common Lisp does out of the box, e.g. lists and other seq's as functions in the function position of an x-expression. There are things Clojure will not do such as reader macros. Clojure's syntax is a bit different, but generally reads cleaner in the same way one might say a font reads cleaner. YMMV.

Re: How to write Common Lisp in 2017 – an initiation manual

#46
Some notes based on my (brief) experience toying with Common Lisp:

* Why hasn't anyone made a more eye-frendly version of the Common Lisp Hyper Spec ? Having good, easily-browsable documentation is a core-problem.

* The relation between the various native data-types were quite unclear to me.

* dealing with the external world was quite a mess. Many project/libraries implementing only half of something and then got abandoned.

* some libraries had a compatibility matrix... with common lisp implementations. that seemed weird to me.

Re: How to write Common Lisp in 2017 – an initiation manual

#47

I'm used to languages like Python, that have a number of files that are modules, and to start a program you run one of them as an entry point. C programs consist of a lot of files that are compiled and linked into a binary executable. Whenever I've tried to learn CL, I couldn't really wrap my head around what the eventual program would be. You build an in-memory state by adding things to it, later dump it to a binary…

I mentioned elsewhere I'm learning Common Lisp. I'm also learning Python by translating some Common Lisp code into Python and part of that is to make sure I understand what the Common Lisp is doing. As an understatement, that's meant building some very unPythonic abstractions (yay, me). Anyway, I think there is a fundamental design difference between Common Lisp and other 'first class' programming languages: Common L…

> Lisp Machine (which was the future when Common Lisp was designed)

Common Lisp was actually designed so that you don't need a Lisp Machine. The people working on it were from CMU (Unix workstations), Lucid (Unix workstations), Franz (Unix/Windows), Apple (Mac), Symbolics (Lispm, PC), Xerox (Lispm, Unix), and many others.

Users used an editor-based IDE (like Franz ELI with GNU Emacs, ILISP with Gnu Emacs), a special IDE usually written in Lisp (Franz, LispWorks, Macintosh Common Lisp, Golden CL on Windows, ...) or even a Lisp Machine which combines the IDE with the operating system.

> copy files between directories

The Symbolics Lisp Listener (REPL + commands) has a command language/interface with a lot of comfort - but with its own usability problems.

You would often type

   Copy File *.lisp.newest >subdir>
instead of using the Lisp function COPY-FILE.

Still today I tend to keep the Lisp IDE running for days/weeks/months... as long as possible. Sometimes Linux tells me I have to restart the machine after some software update...

Re: How to write Common Lisp in 2017 – an initiation manual

#48

i do not know how to message the guy "Scott" author of page, so i am putting this here. in the "LispWorks CL" page, under "Implementations", the "Notes" section elicidates a mystery about the Personal Edition not recognizing the lisp init files. This is actually a limitation in LispWorks Personal Edition which is described on the link provided to retrieve said edition.

[deleted]

Re: How to write Common Lisp in 2017 – an initiation manual

#50
post #46

Some notes based on my (brief) experience toying with Common Lisp: * Why hasn't anyone made a more eye-frendly version of the Common Lisp Hyper Spec ? Having good, easily-browsable documentation is a core-problem. * The relation between the various native data-types were quite unclear to me. * dealing with the external world was quite a mess. Many project/libraries implementing only half of something and then got aba…

> Why hasn't anyone made a more eye-frendly version of the Common Lisp Hyper Spec ? Having good, easily-browsable documentation is a core-problem.

A friend of mine is working on that as we speak. The CLUS, or Common Lisp UltraSpec:

https://phoe.tymoon.eu/clus/doku.php

That said, CLHS isn't bad - it's lightweight, available off-line, and on-line you can pretty much always find what you're looking for by searching for "clhs [term of interest]".

> some libraries had a compatibility matrix... with common lisp implementations. that seemed weird to me.

Common Lisp has a pretty good standard, but it's a bit old so it didn't predict some things we're currently using, and also left some other things to the implementers. So some features are only available via vendor-specific extensions, which makes it necessary for some projects - especially compatibility libraries - to be tested across plethora of CL implementations.

The flip side is that you have a few commercial and open source implementations to choose from, which is valuable if your project can exploit strengths of a particular one.

Post reply on HN