Did someone just reinvent Rebol/Red?
I wish someone would reinvent Rebol/Red with understandable scoping rules. One of the few reasons I don't use the language is because the scoping/binding rules are just completely inscrutable.
Kamby – A programming language based on Lisp that doesn't seem like Lisp
41–50 of 53 posts
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#42By the way, I always wondered why not just take a lisp, put every single thing (even an operator) on a separate line and indent every level of parentheses with a space or two (4 spaces is too much - deep nesting would go too much to the right). So there would be no need for the parentheses in most cases.
People who use lisp like the parentheses.
I don't, though they're no more objectionable than all the {}; languages. I just don't like unnecessary punctuation.
I coded in scheme for years using a preprocessor that understood
define-syntax opt
syntax-rules |
$ _ (x v) b ...
let || x | if (null? x) v | car x
b ...
which is line for line equivalent to (define-syntax opt
(syntax-rules ()
((_ (x v) b ...)
(let ((x (if (null? x) v (car x))))
b ...) )))
It's a matter of taste, but I'd rather read the former. The key ideas, other than using indentation to carry parenthesis level, are to use $ to hang double indents, and | to open a parenthesis that auto-closes.I gave this up learning Clojure so I could use other people's tools. Instead I prefer lighter parentheses, and I use this script to tailor fonts for coding lisp:
https://gist.github.com/Syzygies/226253bc38743ef474ee67cbf58...
I have the most trouble with comment characters, in any language. In various languages I used a preprocessor that implemented a practical version of "comments are flush, code is indented" (hey, it cost me one level) and relied on syntax coloring to mute the comments. Again, I gave this up to use other people's tools.
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#43By the way, I always wondered why not just take a lisp, put every single thing (even an operator) on a separate line and indent every level of parentheses with a space or two (4 spaces is too much - deep nesting would go too much to the right). So there would be no need for the parentheses in most cases.
[0]: https://dwheeler.com/readable/readable-s-expressions.html
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#44Ummmm planet = [ name := 'World' nick := 'Earth' ] 'Hello, ' + (planet :: {WAT}) Output: 10585168
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#45Earlier quoted context omitted.
Seems like an explicit/less confusing way to do variable shadowing, though imho that's not a feature worth implementing in a 400LOC language.
> less confusing way to do variable shadowing How is this less confusing? := vs = will either push a new variable on top of a stack of identically named variables, or change the content of the top element on that stack? Why would anyone want any of that? Shadow variables are usually associated with hard-to-find-bugs, (i.e. forgetting that there is already a variable named 'xyz' in the current scope) not some great fe…
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#46Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#47Earlier quoted context omitted.
Seems like an explicit/less confusing way to do variable shadowing, though imho that's not a feature worth implementing in a 400LOC language.
It being explicit/arbitrary makes it more confusing, not less. At least most languages with variable shadowing, there's a block of some sort that defines the scope. Here it'd just be anywhere that it can change meaning.
In this Kamby language, it looks like the bindings survive and are then accessible by name. When you're executing these [ ... ] blocks, a tree-shaped environment is built up which is then navigated with the :: operator, enabling it to simulate objects with fields.
The idea of there being a stack-like environment of variables which can survive the blocks in which they are bound is very useful in pattern matching and unification.
Under pattern matching, the successful path will have the cumulative variables arising from everything that has successfully matched, including some nested constructs. However, the search strategy will implicitly backtrack in searching for matches, and in backtracking, it will implicitly erase any variables accumulated in the discarded paths.
In the TXR pattern language, I invented some mechanisms for controlling the proliferation of variables. When a pattern function is used, only those variables that correspond to its arguments can emerge.
$ txr -B -c '@(define fun (arg1 arg2))
@(bind arg1 "a1")
@(bind arg2 "a2")
@(bind arg3 "a3")
@(end)
@(fun x y)'
Output: y="a2"
x="a1"
How it works is that the unbound variables x and y are identified with the arg1 and arg2 variables. The pattern function executes, binding arg1, arg2 and arg3. Then a resolution step is done at return-time. Because arg1 was identified with unbound x, x now receives that binding. Similar for y. The variable arg3 disappears; that entire local environment of the function is discarded, and x and y are grafted onto the original environment that existed on entry into the function.If we bind an argument, the parameter will be bound on entry into the function, and so then has to unify in the subsequent bind directive. It does if we pass the value "a1":
txr -B -c '@(define fun (arg1 arg2))
@(bind arg1 "a1")
@(bind arg2 "a2")
@(bind arg3 "a3")
@(end)
@(fun "a1" y)'
y="a2"
fails if we pass some other value: txr -B -c '@(define fun (arg1 arg2))
@(bind arg1 "a1")
@(bind arg2 "a2")
@(bind arg3 "a3")
@(end)
@(fun "foo" y)'
false
The variable binding environment isn't reified as a value that can itself be bound as a variable and inspected; in any context, there is one environment which contains everything that was done in the chain of pattern matching leading up to that point; dead ends that were backtracked out of are gone.Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#48By the way, I always wondered why not just take a lisp, put every single thing (even an operator) on a separate line and indent every level of parentheses with a space or two (4 spaces is too much - deep nesting would go too much to the right). So there would be no need for the parentheses in most cases.
Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#49By the way, I always wondered why not just take a lisp, put every single thing (even an operator) on a separate line and indent every level of parentheses with a space or two (4 spaces is too much - deep nesting would go too much to the right). So there would be no need for the parentheses in most cases.
Another technical reason is that we work with text based version control tools, under which we use whitespace-insensitive diff as a hack to hide some differences that don't make a difference. That tool becomes unreliable over indentation-only languages; you can make a semantic change whose whitespace-insensitive diff is empty.
Another technical reason not to go indentation-only is that you don't know whether a partially obscured block of code is complete or just a prefix:
|defun foo():
| bar()
| xyzzy()
+----------
am I looking at all of foo, or do I have to scroll down to see more?Here you know it's the whole thing:
|(defun foo():
| (bar)
| (xyzzy))
+---------- Re: Kamby – A programming language based on Lisp that doesn't seem like Lisp
#50Earlier quoted context omitted.
Lisp code tends to have fewer delimiting punctuation characters than most algol style current languages. I think people tend to dislike languages that have only the minimum necessary, because it's easy to misread code then and redundancy helps compilers catch mistakes as inconsistent syntax. But there's always Forth for the the lighter taste in delimiters: https://github.com/TexTerry/forth-examples/blob/master/pasca.…
I never understand these complaints about parenthesis, my editor takes care of them. Interestingly people never complain about the inconsequences in mathematical notation, i.e. infix operators like plus or minus (e.g. 3+5), postfix operators like faculty (i.e. 9!) and last but not least prefixed user defined funtions like f(x). But as Lisp was my first real language, I might be a bit biased. And besides Lisp I like l…