I'm trying to write a snippet whose inputs (tab-stop fields) are two numbers, and which returns their sum. But I don't know how to reference the values of both fields at the same time, and it seems like I can't reference the values of the tab-stop within embedded elisp code.
Here is what I tried:
First number: $1
Second number: $2
Sum of two numbers: `(+ (string-to-number $1) (string-to-number $2))`
But when I expand the snippet, the text [yas] elisp error! appears where the sum should go. What am I doing wrong?
joaotavora recently pointed out that this can be done using yas-field-value:
First number: ${1:0}
Second number: ${2:0}
Sum of two numbers: ${2:$(+ (string-to-number (or (yas-field-value 1) "0")) (string-to-number (or yas-text "0")))}
and sorry for the confusion. According to the official snippet writing guide, what you are looking for is called a mirror. Unfortunately, a mirror can only mirror a single variable, so you seem to be out of luck.
This is probably because yasnippet needs to know which mirrors to update when you type a field. (It doesn't want to update them all, because that could be costly), so it needs a way of determining which mirrors are affected by which fields. If it allowed arbitrary substitutions, that would be impossible to determine. (A simple keyword search isn't enough because the variable could be hidden behind metaprogramming).
Related
I made all URLs clickable by:
(define-globalized-minor-mode global-goto-address-mode goto-address-mode goto-address-mode)
(global-goto-address-mode)
However, when I have a shell command with "service:" substring, Emacs treats it as a link incorrectly. How can I remove that link type?
Emacs 27.1 makes this a bit more configurable via the two new variables:
goto-address-uri-schemes-ignored
goto-address-uri-schemes
You should set only one of the two and, per the docstrings, must do so before the goto-addr library is loaded. This is because the new variables are only intermediate values1 which are used when defining goto-address-url-regexp -- which (as before) is the only value which is ultimately used by the library.
If you wish to change the behaviour after loading goto-addr then you need to re-generate or otherwise set goto-address-url-regexp, exactly the same as in earlier versions. See my original answer for an example of doing this.
1 Specifically, goto-address-uri-schemes-ignored affects the default value of goto-address-uri-schemes, which in turn affects the default value of goto-address-url-regexp.
Try this:
(setq goto-address-url-regexp
(concat "\\<"
(regexp-opt (cl-delete-if
(lambda (x)
(member x '("mailto:" "data:" "service:")))
(copy-sequence thing-at-point-uri-schemes))
:paren)
thing-at-point-url-path-regexp))
This should also fix bugs in the original regexp, so it could match some new things as well, but probably nothing you're worried about ("svn+ssh://" and "bzr+ssh://" will match now, and a few others will be more constrained where dots are concerned. Basically the original code didn't regexp-quote the schemes!)
Note that "mailto:" and "data:" were being excluded in the original.
This passage from On Lisp is genuinely confusing -- it is not clear how returning a quoted list such as '(oh my) can actually alter how the function behaves in the future: won't the returned list be generated again in the function from scratch, the next time it is called?
If we define exclaim so that its return value
incorporates a quoted list,
(defun exclaim (expression)
(append expression ’(oh my)))
Then any later destructive modification of the return value
(exclaim ’(lions and tigers and bears))
-> (LIONS AND TIGERS AND BEARS OH MY)
(nconc * ’(goodness))
-> (LIONS AND TIGERS AND BEARS OH MY GOODNESS)
could alter the list within the function:
(exclaim ’(fixnums and bignums and floats))
-> (FIXNUMS AND BIGNUMS AND FLOATS OH MY GOODNESS)
To make exclaim proof against such problems, it should be written:
(defun exclaim (expression)
(append expression (list ’oh ’my)))
How exactly is that last call to exclaim adding the word goodness to the result? The function is not referencing any outside variable so how did the separate call to nconc actually alter how the exclaim function works?
a) the effects of modifying literal lists is undefined in the Common Lisp standard. What you here see as an example is one possible behavior.
(1 2 3 4) is a literal list. But a call to LIST like in (list 1 2 3 4) returns a freshly consed list at runtime.
b) the list is literal data in the code of the function. Every call will return exactly this data object. If you want to provide a fresh list on each call, then you need to use something like LIST or COPY-LIST.
c) Since the returned list is always the same literal data object, modifying it CAN have this effect as described. One could imagine also that an error happens if the code and its objects are allocated in a read-only memory. Modifying the list then would try to write to read-only memory.
d) One thing to keep in mind when working with literal list data in source code is this: the Lisp compiler is free to optimize the storage. If a list happens to be multiple times in the source code, a compiler is allowed to detect this and to only create ONE list. All the various places would then point to this one list. Thus modifying the list would have the effect, that these changes could be visible in several places.
This may also happen with other literal data objects like arrays/vectors.
If your data structure is a part of the code, you return this internal data structure, you modify this data structure - then you try to modify your code.
Note also that Lisp can be executed by an Interpreter. The interpreter typically works on the Lisp source structure - the code is not machine code, but interpreted Lisp code as Lisp data. Here you might be able to modify the source code at runtime, not only the data embedded in the source code.
I'm trying to emulate Lisp-like list in JavaScript (just an exercise with no practical reason), but I'm struggling to figure out how to best represent an empty list.
Is an empty list just a nil value or is it under the hood stored in a cons cell?
I can:
(car '())
NIL
(cdr '())
NIL
but an empty list for sure can not be (cons nil nil), because it would be indistinguishable from a list storing a single nil. It would need to store some other special value.
On the other hand, if an empty list is not built from a cons cell, it seems impossible to have a consistent high-level interface for appending a single value to an existing list. A function like:
(defun append-value (list value) ...
Would modify its argument, but only if it is not an empty list, which seems ugly.
Believe it or not, this is actually a religious question.
There are dialects that people dare to refer to as some kind of Lisp in which empty lists are conses or aggregate objects of some kind, rather than just an atom like nil.
For example, in "MatzLisp" (better known as Ruby) lists are actually arrays.
In NewLisp, lists are containers: objects of list type which contain a linked list of the items, so empty lists are empty containers. [Reference].
In Lisp languages that aren't spectacular cluster-fumbles of this sort, empty lists are atoms, and non-empty lists are binary cells with a field which holds the first item, and another field that holds the rest of the list. Lists can share suffixes. Given a list like (1 2 3) we can use cons to create (a 1 2 3) and (b c 1 2 3) both of which share the storage for (1 2 3).
(In ANSI Common Lisp, the empty list atom () is the same object as the symbol nil, which evaluates to itself and also serves as Boolean false. In Scheme, () isn't a symbol, and is distinct from the Boolean false #f object. However Scheme lists are still made up of pairs, and terminated by an atom.)
The ability to evaluate (car nil) does not automatically follow from the cons-and-nil representation of lists, and if we look at ancient Lisp documentation, such as the Lisp 1.5 manual from early 1960-something, we will find that this was absent. Initially, car was strictly a way to access a field of the cons cell, and required strictly a cons cell argument.
Good ideas like allowing (car nil) to Just Work (so that hackers could trim many useless lines of code from their programs) didn't appear overnight. The idea of allowing (car nil) may have appeared from InterLisp. In any case, Evolution Of Lisp paper claims that MacLisp (one of the important predecessors of Common Lisp, unrelated to the Apple Macintosh which came twenty years later), imitated this feature from InterLisp (another one of the significant predecessors).
Little details like this make the difference between pleasant programming and swearing at the monitor: see for instance A Short Ballad Dedicated to the Growth of Programs inspired by one Lisp programmer's struggle with a bletcherous dialect in which empty lists cannot be accessed with car, and do not serve as a boolean false.
An empty list is simply the nil symbol (and symbols, by definition, are not conses). car and cdr are defined to return nil if given nil.
As for list-mutation functions, they return a value that you are supposed to reassign to your variable. For example, look at the specification for the nreverse function: it may modify the given list, or not, and you are supposed to use the return value, and not rely on it to be modified in-place.
Even nconc, the quintessential destructive-append function, works that way: its return value is the appended list that you're supposed to use. It is specified to modify the given lists (except the last one) in-place, but if you give it nil as the first argument, it can't very well modify that, so you still have to use the return value.
NIL is somewhat a strange beast in Common Lisp because
it's a symbol (meaning that symbolp returns T)
is a list
is NOT a cons cell (consp returns NIL)
you can take CAR and CDR of it anyway
Note that the reasons behind this are probably also historical and you shouldn't think that this is the only reasonable solution. Other Lisp dialects made different choices.
Try it with your Lisp interpreter:
(eq nil '())
=> t
Several operations are special-cased to do unorthogonal (or even curious :-) things when operating on nil / an empty list. The behavior of car and cdr you were investigating is one of those things.
The idenity of nil as the empty list is one of the first things you learn about Lisp. I tried to come up with a good Google hit but I'll just pick one because there are so many: http://www.cs.sfu.ca/CourseCentral/310/pwfong/Lisp/1/tutorial1.html
I want to use the capture module of org-mode to create a data base of new words that I want to learn, and then use the drill module to learn them (flash cards style).
In my org-capture-templates I added the following:
("v" "Vocabulary" entry
(file+headline (concat org-directory "/vocab.org")
"Vocabulary")
"* Word :drill:\n%^ \n** Answer \n%^")
This is a rather naive template which I borrowed from here. It works fine but it is too limited. Unfortunately I'm rather new to elisp and I don't know how to improve it.
I think the above template has to be improved in the following there aspects:
Headline Currently the first input string is the (new) word and the headline is fixed. How can the headline be the same (input) word? I think that the following result is desirable:
* Vocabulary
** Foo :drill:
Foo
*** Answer
What is foo
Actually an even better way would be to have 3 input strings.
The new word (for example foo) which will be the headline.
If the second is empty, then it gets the same string as (1). Otherwise, concatenates the string to the one from (1). E.g. having as second input bar would yield foo bar. This will be the content of the entry.
The word's definition which should come in the answer sub-headline.
Duplications (see again this) If at some later point I try to capture foo again, I would like to know it, and be directed to edit the already existing entry - skipping all the inputs.
Sorting After capturing I think it would be nice to sort the list of words. This should not be too hard given that the headline of each entry is the word itself. In this case one can probably use the org-sort-entries function.
I know this is a rather big questions but I also think that if it can be solved here it will be of great use to many users.
Edits:
Using #juan_g suggestions, I improved my template and now it is:
("v" "Vocabulary" entry
(file+headline (concat org-directory "/vocab.org")
"Vocabulary")
"* %^{The word} :drill:\n %t\n %^{Extended word (may be empty)} \n** Answer \n%^{The definition}")
I didn't manage to set the default value of the second input to be the 1st one. I tried something like %^{Extended word (may be empty)|%\1} but it returns ^A which is not helpful.
In any case, this improved version seems to be already usable.
About the input question, in Org Mode Manual: 9.1.3.2 Template expansion, there is the %\1 special escape code:
%\n Insert the text entered at the nth %^{prompt}, where n a number, starting from 1.
The duplications question probably would need some Emacs Lisp coding.
For sorting, see C-c ^ (org-sort).
BTW, org-drill seems indeed a really interesting package, based on SuperMemo's spaced repetition algorithms.
You need an extra "\", therefore %\\1 works as expected.
Ok I need some help with thinking through this conceputally.
I need to check if a list and another list is structurally equal.
For example:
(a (bc) de)) is the same as (f (gh) ij)), because they have the same structure.
Now cleary the base case will be if both list are empty they are structurally equal.
The recursive case on the other hand I'm not sure where to start.
Some ideas:
Well we are not going to care if the elements are == to each other because that doesn't matter. We just care in the structure. I do know we will car down the list and recursively call the function with the cdr of the list.
The part that confuses me is how do you determine wheter an atom or sublist has the same structure?
Any help will be appreciated.
You're getting there. In the (free, online, excellent) textbook, this falls into section 17.3, "Processing two lists simultaneously: Case 3". I suggest you take a look.
http://www.htdp.org/2003-09-26/Book/curriculum-Z-H-1.html#node_toc_node_sec_17.3
One caveat: it looks like the data definition you're working with is "s-expression", which you can state like this:
;; an s-expression is either
;; - the empty list, or
;; - (cons symbol s-expression), or
;; - (cons s-expression s-expression)
Since this data definition has three cases, there are nine possibilities when considering two of them.
John Clements
(Yes, you could reduce the number of cases by embedding the data in the more general one that includes improper lists. Doesn't sound like a good idea to me.)