A series of notes that I learn Emacs hacking. Cask and pallet package for multi-version Emacs collaboration; Macro in emacs-lisp; use-package package introduction.
Prologue: Not too much for day 8. Previous video is 1 hour’s long, the author decrease the length of each video to 30 min for better performance. Therefore I put the content in two days’ video into single post.
cask install in the terminal to merge the package directory.
Now we can get rid of the previous package initialization code.
mwe-log-command package
M-x mwe:open-command-log-buffer
Now we can have an idea on what key is pressed in history.
Day 9
Macro
We can consider it as “code that generates code”.
Analog as macro in C or template in C++.
See an example below
1
2
(defmacroinc(var)(list'setqvar(list'1+var)))
Usage of the example
1
2
3
(setqmy-var1)(incmy-var)(macroexpand'(incmy-var))
Write macro is similar as writing function in elisp.
However, to achieve similar result we can use defun, why bother? What’s the difference between function and macro?
Evaluation: the macro arguments are the actual expressions appearing in the macro call. For functions, the value in the argument is first fetched or calculated then the function is executed. For macro, the expression is first expanded and then executed.
Expansion: the value returned by the macro body is an alternate Lisp expresion, aka the expansion of the macro.
Backquote matters. Emacs will automatically insert two backquotes all together. Use the following code to disable it.
1
(sp-local-pair'emacs-lisp-mode"`"nil:actionsnil)
Backquote ` works with ,. It means we do not execute the program after the quote. However, the expression (program) after , will be execute first, and then pass as argument.
(defunmy-print(number)(message"%d"number))(my-print2)(my-print(+23))(defmacromy-print-2(number)`(message"%d",number))(my-print-22)(my-print-2(+23))(defmacroinc(var)(list'setqvar(list'1+var)))(setqmy-var-2)(incmy-var)(defmacroinc2(var1var2)(list'progn(list'incvar1)(list'incvar2)))(macroexpand'(inc2my-varmy-var));; this will expand only one layer.(macroexpand-all'(inc2my-varmy-var))
use-package package
All the stuff can be found on its official page.
(use-package xxx): a better solution to substitute (require 'xxx). If the ‘xxx’ is not in elpa, we will encounter an error if we use require. However, use-package can help you load packages safer.
We can merge similar configuration together by using :init and :config. The difference is that, :init will be executed before requiring the package, while :config will be executed after loading the pacakge, when we can add more configuration to the package.
require will load everything, which is too slow. We can use autoload instead. Now we can integrate autoload into use-package. Use :command to do so. :defer is equal to eval-after-load.