I use k/q regularly, and I'm not using it for "math".
The compact notation creates value in helping you make correct programs. See [1] and [2] specifically.
[1]: https://news.ycombinator.com/item?id=8476294
[2]: https://news.ycombinator.com/item?id=8476702
You can write C in a dense style as well. And I do. When I do this, I can see opportunities for reuse that I cannot see if I spread my C program across multiple pages and multiple files. Here is the bulk of my webserver[3] that will beat the pants off of any other webserver -- substantially faster than nodejs or kdb's own webserver[4], and probably nginx or anything else you've got. (PS: If you think you know of a faster one, I'd like to know about it).
I am telling you I can only do this because the code is small.
Let me refer you to the TechEmpower framework benchmarks: https://www.techempower.com/benchmarks/#section=data-r17&hw=...
Look at the language column there, you'll be surprised.
$ wrk -t2 -c90 -d9s http://localhost:8080/plaintext
Running 9s test @ http://localhost:8080/plaintext
2 threads and 90 connections
Thread Stats Avg Stdev Max +/- Stdev
Latency 831.78us 364.48us 7.56ms 70.19%
Req/Sec 40.55k 3.31k 48.04k 74.44%
726417 requests in 9.01s, 87.98MB read
Requests/sec: 80603.64
Transfer/sec: 9.76MB
which I got by checking out https://github.com/TechEmpower/FrameworkBenchmarks.git, disabling the mysql connection, and running frameworks/Go/fasthttp's ./server-mysql (which is what the benchmark script seems to do). I thought this would be easier than getting dash running the TechEmpower results.and here's dash running with the kdb networking disabled (best of three):
$ wrk -t2 -c90 -d3s 'http://127.0.0.1:8080/?f=204&k=hi&v=1'
Running 3s test @ http://127.0.0.1:8080/?f=204&k=hi&v=1
2 threads and 90 connections
Thread Stats Avg Stdev Max +/- Stdev
Latency 787.72us 213.62us 3.49ms 71.85%
Req/Sec 44.82k 3.04k 60.44k 83.61%
271946 requests in 3.10s, 16.08MB read
Requests/sec: 87671.23
Transfer/sec: 5.18MB
My laptop isn't a beefy "Dell R440 Xeon Gold + 10 GbE" -- this is just a loopback test, but it's already disinclined me to spend any more time on it; Fasthttp definitely is impressive how close it gets, but dash is still faster.And comparing a 100 line C program to hundreds or thousands of lines of go or C or Java is a bit pointless. If the 100 lines of C doesn't do what you want, I'll throw it away and write a different 100 lines. That's what brief programs get you.
NB: I would have tried ulib but it wouldn't even build on my laptop.
The Lisp-like way of programming is more appealing to me because it makes the programs very easy to read. You can mostly get a sense of what they're doing just by reading them like ordinary English. I've found this especially useful when I'm trying to understand code I'm not already familiar with, or when looking at my own code months or years from when I wrote it, and it's especially important these days when polyglot programming is commonplace -- I don't need to remember nearly as much of how to do something in Lisp because it's so easy and straightforward and doesn't have the overhead of remembering a whole bunch of specialized syntax.
Contrast this with the terser, more mathematically-inclined languages, where specialized syntax and single-character names are widely used. These tend to be more write-only languages for me, where I have to be constantly steeped in the language in order to make understanding it relatively natural, and if I go away from them for a while, it takes quite a bit of effort to get back in to them enough to make sense of what was written, and reading other people's code is much more of a chore than it is for me in Lisp.
In the old days, or perhaps on embedded systems these days, when one had to closely watch the byte count of one's program lest it not fit in to memory, perhaps such terseness was useful. But these days, I'm not yet convinced of its utility outside of a mathematical context, where the mapping of such terse names and operations is more natural.
For me clarity trumps terseness.
I don't just do this with APLish languages; I do this with C (and lisp, and PHP, and others...)
I've only ever written short programs correctly: If they can fit on a page, I can just look and see whatever bug I might be experiencing.
If someone wants to change my software, it's because they want it to do something that I don't want it to do. They will find value in the fact it is short: That there isn't very much to read. Admittedly, a programmer unexperienced in this method may have some anxieties about it, but given how valuable correctness is, I'd prefer to cause a bit of anxiety in beginners than make programs that need beginners to fix them.
When we learn to read, we learn to "sight read" words. APL/J/K constructs can be "sight read" as well.
I'd argue that much less of this is required for languages like Lisp, unless, of course, you step away from practicing reading English, in which case maybe the very English-like programs of Lisp will start to seem foreign to you.
Lots of things lend themselves well to pointfree style, and if you do not see them it is because of your own horizons.
You can write OCaml/Haskell with names like doesFileExist when you need to.
You can, but it's rarely done in practice. This is a cultural issue more than a language issue. OCaml/Haskell programmers just seem to prefer much shorter, more math-like names than Lisp programmers do.
For me this makes a huge difference when reading through code written by the community. Lisp is just much more immediately understandable than OCaml/Haskell and related languages.
Yes, this is probably my own limitation, and I'd probably be a lot better at it given enough practice. But I just don't need that much practice to understand Lisp, and I can go away from it and come back to it much later without needing a significant refresher in the language either.
What APL does well is filter/select/transform more spreadsheet style work than linear algebra stuff. It's a language to describe computation as meant by the sort of computer scientists that were born when computer was a job description.
Come to think of it, that's similar to what's often done to lists in Lisp, outside of the more traditional control flow of 'business logic.' Precisely the filter-select-transform.
I wonder if APL is that much different from Matlab by the concept.
https://github.com/Co-dfns/Co-dfns https://news.ycombinator.com/item?id=13565743 https://news.ycombinator.com/item?id=13638086 https://news.ycombinator.com/item?id=13797797
Even though the set of short symbols has to be limited, don't we currently have a few dozen often-repeated operations in language keywords and standard libraries? (Especially in the approach of e.g. Clojure, relying heavily on combining standard transformations on strictures.)