The following notes were taken while discussing Chapter 5 of the book Mastering Emacs by Mickey Petersen (2022 edition) in book discussion group meetings.

An index of notes for all chapters are available at notes.html.

{{ toc }}

## Killing Text

Killing text is equivalent to what we call as cutting text in other editors. Killing some text removes the text from the buffer and adds it to the kill ring. The kill ring is the clipboard of Emacs.

To discover kill commands using the apropos functionality, type `C-h a ^kill-`.

Here is a list of commands introduced in the first section of this chapter:

- `C-d`: Delete the next character.
- `<backspace>`: Delete the previous character.
- `M-d`: Kill until the end of a word.
- `C-<backspace>`: Kill backward until the beginning of a word.
- `C-k`: Kill the rest of the current line.
- `M-k`: Kill until the end of sentence.
- `C-M-k`: Kill expression following point.
- `C-S-<backspace>`: Kill current line. Does not work in terminal Emacs. Use `C-a C-k` as alternative.
- `C-w`: Kill text between point and mark.
- `M-w`: Copy text between point and mark to kill ring.
- `C-M-w`: Cause the following command, if it kills, to append to the last stretch of text in the kill ring.
- `C-y`: Yank (paste) the last stretch of text in the kill ring to the buffer.
- `M-y`: Cycle through kill ring.

I have observed that some Emacs users do not bother using `M-w` to copy to kill ring. Instead they type `C-w C-/` to cut the text and immediately undo the cut which effectively leaves the buffer unchanged but inserts a copy of the text that was cut into the kill ring. For example, while `C-a C-SPC C-n C-n M-w` copies two lines into the kill ring, so does `C-a C-SPC C-n C-n C-w C-/`. The latter key sequence avoids having to use `M-w` but it is worth noting that this key sequence does not work in a readonly buffer while the former does. To quickly see the difference, open `/etc/hosts` as a non-root and non-privileged user and try both the key sequences. The former key sequence does not modify the buffer, so it works perfectly in a readonly buffer. The latter key sequence modifies the buffer when we type `C-w`, so it does not work in a readonly buffer.

I have also observed that many Emacs users do not bother learning `C-S-<backspace>` because they can achieve the same results using `C-a C-k`. Further, `C-S-<backspace>` does not work in terminal Emacs due to terminal limitations. The key sequence `C-a` moves the cursor to the beginning of the line and `C-k` kills everything until the end of the line.

There is a difference between deleting and killing. The first two commands `C-d` and `<backspace>` delete characters but the deleted characters are not added to the kill ring. The remaining commands in the list above kill text, i.e. remove the text from the buffer and add it to the kill ring. The killed text can be pasted into the buffer using `C-y`. For example, `M-d M-d M-d C-p C-p C-y` kills the next three words and pastes them two lines above.

## Append Kill

The key sequence `C-M-w` is used to ensure that if the next command happens to be a kill command, then the killed text is appended to the last stretch of text in the kill ring.

To understand what this command does we must first understand that after a kill command adds a new stretch of text to the kill ring, subsequent consecutive kills append to the same stretch of text in the kill ring, i.e. consecutive kills form a single large stretch of text in the kill ring. This can be tested by performing consecutive kills and then pasting with `C-y`. For example, `M-d M-d M-d C-p C-p C-y` kills 3 words, creates a single stretch of text consisting of those 3 words in the kill ring and pastes that text two lines above.

However, the moment a non-kill command is used, it seals the stretch of text in the kill ring. Any subsequent kill command begins a new stretch of text. For example, `M-d M-d M-d C-p M-d M-d C-p C-y` kills 3 words at first but then it moves to the previous line sealing that kill text consisting of 3 words. Then it kills 2 words and creates a new stretch of text in the kill ring. Therefore, the final yank command pastes only those 2 words from the kill ring.

This can be a problem if we want to kill text from various parts of the buffer and yet create a single stretch of text that we want to paste somewhere. That's when `C-M-w` comes useful. For example, `M-d M-d M-d C-p C-M-w M-d M-d C-p C-y` kills 3 words and creates a single stretch of text in the kill ring consisting of those 3 words. Then it moves one line up and kills 2 more words but this time it appends those 2 words to the existing stretch of text in the kill ring. Finally, it moves two lines up and pastes the entire stretch of text consisting of 5 words into the buffer.

## Digit and Negative Arguments

Here are some complete key sequences that demonstrate digit and negative arguments:

- `M-3 M-d`: Kill the next 3 words.
- `M- M-d` : Kill the previous word.
- `M-- M-3 M-d` : Kill the previous 3 words.
- `C-M-3 C-M-k`: Kill the next 3 expressions.
- `C-M-- C-M-k`: Kill the previous expression.
- `C-M-- C-M-3 C-M-k`: Kill the previous 3 expressions.

## Yanking Text

There are two key bindings to learn here. The key sequence `C-y` executes the `yank` command which yanks the last stretch of text from the kill ring.

In the apropos system, `paste` is a synonym of `yank`. Type `C-h v apropos-synonyms RET` to see all the synonyms define for the apropos system. Thus `C-h a paste RET` includes the results for `yank` too.

## Yank Pop

The key sequence `M-y` executes the `yank-pop` command which replaces a just-yanked kill with an older kill. This key sequence helps us to cycle through the kill ring and fetch older and older kills to be pasted into the buffer.

Here is an experiment to see how we can use `C-y` and `M-y` can be used together:

1. Open a new buffer and type these five words in a single line: `foo bar baz qux quux`.
2. Then type `C-a M-d C-g M-d C-g M-d`. At this point three stretches of text have been inserted into the kill ring. The `C-g` between every `M-d` is there to avoid appending kills to the existing stretch of text in the kill ring. This ensures that we have three separate stretches of text in the kill ring.
3. Now type `C-y`. The last stretched of kill text, i.e. `baz` is now pasted into the buffer.
4. Now without typing any other key sequence, type `M-y`. The earlier pasted text `baz` is now replaced with an older stretch of text from the kill ring. Thus `baz` is replaced with `bar`.
5. Now once again type `M-y`. The earlier pasted text `bar` is now replaced with a further older stretch of text from the kill ring. Thus `bar` is replaced with `foo`.

Note in the previous steps how we are not supposed to type any other key between the first `C-y` and `M-y`. Similarly, while cycling through the kill ring, we must not type any other key between the consecutive `M-y` key sequences. While cycling through the kill ring, when we reach the oldest kill, the next `M-y` wraps around and brings back the newest kill.

Since Emacs 28, the key sequence `M-y` also supports browsing the kill ring and yanking any arbitrary entry from the kill ring. For example, after trying the above experiment, type `C-g` just to make sure that we are breaking any existing `C-y` or `M-y` cycle. Then type `M-y` and a minibuffer prompt appears to yank an arbitrary kill from the kill ring. If we remember the previous kill, we can type it out partially and type `TAB` to autocomplete it. Alternatively, we could also type `TAB` initially itself to browse all the kills in the kill ring.

## Maximum Length of Kill Ring

Type `C-h v kill-ring-max RET` to see the maximum length of the kill ring. It is `60` by default.

## Killing Lines

Since `C-S-<backspace>` works only in GUI Emacs and not in terminal Emacs due to terminal limitations, in the section Killing Lines the author recommends installing the package `whole-line-or-region` which modifies the behaviour of `C-w` to kill the current line if there is no active region.

This package can be installed with the following command:

    M-x package-install whole-line-or-region RET

Then a mode offered by this package can be enabled by adding this line to the Emacs initialisation file:

    (whole-line-or-region-global-mode)

After Emacs is started with the updated initialisation file, typing `C-w` kills the current line if there is no active region. However, if there is an active region then `C-w` retains the default behaviour of killing the region.

Although the author recommends this package, I do not use this package. I have found `C-a C-k` to be very effective for killing the current line. However, it is worth noting that for non-empty lines, `C-k` does not include the newline in the kill by default. If we want to remove the newline too, we must type `C-k` another time. Therefore, to faithfully reproduce the behaviour of `C-w` (of `whole-line-or-region`) or that of `C-S-<backspace>`, we need to type `C-a C-k C-k`.

It is possible to change the default behaviour of `C-k` such that when we type it at the beginning of a line, the trailing newline is included in the kill. To do so, add this to the Emacs initialisation file:

    (setq kill-whole-line t)

After Emacs is started with this initialisation file, `C-k` kills a whole line along with the trailing newline only if cursor is at the start of a line. In other words, with this setting, `C-a C-k` always kills a whole line along with the trailing newline.

## Transpose

Here are some transpose commands:

- `C-t`: Interchange characters around point.
- `M-t`: Interchange words around point.
- `C-M-t`: Interchange expressions around point.
- `C-x C-t`: Exchange current line and previous line.
- `M-x transpose-paragraphs RET`: Interchange current paragraph with next one.
- `M-x transpose-sentences RET`: Interchange the current sentence with the next one.

While using `C-t` remember that the point is the logical place between two characters. For example if the cursor blinking on the letter `e` of the word `hello`, then the point is between the letters `h` and `e`. When we type a new character, the new character is inserted where the point is. The key sequence `C-t` interchanges the characters on both sides of the point, i.e. it exchanges the character the cursor is blinking on with the character just before it.

There is a subtle difference between the way `C-x C-t` works and the way the other commands work. The other commands exchange the current or previous object with the next one. However, `C-x C-t` exchanges the current line with the previous one.

Note that the cursor moves to the end of the next object after performing an exchange. This allows the object that moved forward to be dragged further forward by repeated application of the same command. Note again that while the other commands drag the thing at point forward, `C-x C-t` drags the previous line forward.

If the cursor is on a space between `"foo" :: "bar"`, note that `M-t` will transpose it to `"bar" :: "foo"` because it ignores symbols.

## Filling

Here are some complete key sequences that perform paragraph filling:

- `M-q`: Refill paragraph.
- `C-u M-q`: Refill paragraph and justify text too.
- `C-x f 40 RET`: Set `fill-column` to 40.
- `C-x .`: Set the fill prefix to the current line up to point. On performing a fill operation, the fill prefix is inserted at the beginning of every new line created.
- `C-a C-x .`: To cancel the fill prefix, type `C-x .` at the beginning of a line. Thus `C-a C-x .` cancels the fill prefix.
- `M-x auto-fill-mode RET`: Toggle auto-filling.

## Commenting

Here are some key bindings to add comments to code in various ways:

- `M-;`: Insert or remove comment in a do what I mean (DWIM) fashion. If the line is empty, a comment is inserted at the beginning of the line. If the line is not empty, a comment is inserted at the end of the line and then indented to the column numbered `comment-column` if it can. If a region is selected, it comments or uncomments that region.
- `C-x C-;`: Comment out or uncomment the current line.
- `M-x comment-box RET`: Comment a region by drawing a box made of comment characters around the selected region. Running this command repeatedly on the same region creates multiple nested comment boxes.
- `M-j`: Insert a new line and continue with the comment if the current line has an open comment. If there is no open comment in the current line, then create a new line and indent.
- `C-M-j`: Same as above.

Here are some variables that control the behaviour of comment-related commands:

- `comment-style`: The default is `indent` which ensures that new comments created with the comment commands are correctly indented.
- `comment-styles`: An association list with all the available comment styles.
- `comment-start`: String to insert to start a new comment.
- `comment-end`: String to insert to end a new comment.
- `comment-padding`: Extra spacing between the comment characters and the comment text. This is the minimum number of spaces (only if the value of this variable is made of spaces) that Emacs tries to keep between the comment characters and comment text. No spaces are inserted if `comment-start` and `comment-end` already provide `comment-padding` number of spaces or more to separate the comment text.

To demonstrate how changing `comment-style` changes the commenting behaviour try `M-x (setq comment-style 'indent) RET`, then select a region and type `M-;`. The selected region will be commented out with a comment box.

However running `M-x (setq comment-style 'aligned) RET`, selecting a region in a C buffer and typing `M-;` does not seem to do anything interesting.

## Search and Replace

Here are some complete key sequences that demonstrate search and replace commands:

- `M-% foo RET bar RET`: Replace the string `foo` with `bar` while prompting for instruction at every match.
- `C-M-% f.. RET bar RET`: Replace matches for regular expression `f..` with `bar` while prompting for instruction at every match.
- `M-x query-replace RET foo RET bar RET`: Same as `M-% foo RET bar RET`.
- `M-x query-replace-regexp RET f.. RET bar RET`: Same as `C-M-% f.. RET bar RET`.
- `M-x replace-string RET foo RET bar RET`: Replace the string `foo` with `bar` but do not prompt for instruction at every match.
- `M-x replace-string RET f.. RET bar RET`: Replace matches for regular expression `f..` with `bar` but do not prompt for instruction at every match.

The following key bindings work while a query replace operation is in progress:

- `y`: Replace one match and continue.
- `SPC`: Same as `y`.
- `n`: Skip to next match.
- `DEL`: Same as `n`.
- `q`: Exit query replace.
- `RET`: Same as `q`.
- `.`: Replace one match and exit.
- `,`: Replace and stay at current match.
- `!`: Replace all remaining matches in the buffer with no more questions.
- `^`: Move point back to the previous match.
- `u`: Undo previous replacement.
- `U`: Undo all replacements.
- `E`: Edit replacement string and replace next match.

Just like incremental search (`C-s` or `C-M-s`), search and replace performs case folding, i.e. performs case-insensitive match if the search string is a lowercase string. However, the moment we include an uppercase character in the search string, search and replace performs case-sensitive search and replace.

## Regular Expressions

This section presents some examples of regular-expression-based search as well as search-and-replace. Here is a simple text buffer where the commands to be presented later can be tried out.

    foo-bar-baz
    foo-baar-baz
    foo-baaar-baz
    foo-baaaar-baz
    foo-baaaaar-baz
    foo-baaaaaar-baz

    web
    server
    webserver
    web server
    web_server
    web->server
    web::server
    web.server
    securewebserver
    secure web server
    web server port 80

    web-server
    web-api-server
    secure-web-server
    web-server-port-80
    web-server-port-http
    web-server-port-HTTP-80

    (1, 2, 3)
    [4, 5, 6]
    {7, 8, 9}
    ((10 + 20) * 30)
    <40, 50, 60>

    "hello, world"
    'hello, world'

    ; comment
    # comment
    // comment
    /* comment */

Here are some complete key sequences that demonstrate regular expressions in search operations:

- `C-M-s f..`: Search for the letter `f` followed by two characters.
- `C-M-s foo\|bar`: Search for the string `foo` or `bar`.
- `C-M-s ba\{3\}r`: Search for the letter `b` followed by the string `aaa` and the letter `r`.
- `C-M-s ba\{3,5\}r`: Search for the letter `b` followed by 3 to 5 repetitions of the letter `a` followed by the letter `r`.
- `C-M-s port-[0-9]+`: Search for the string `port-` followed by one or more digits.
- `C-M-s port-[[:digit:]]+`: Same as above.
- `C-M-s port-[[:alnum:]]+`: Search for the string `port-` followed by one or more alphanumeric characters.
- `C-M-s port-[[:upper:][:digit:]-]+`: Search for the string `port-` followed by consecutive sequence of one or more upper-case letters, digits or hyphen.
- `C-M-s \<web`: Search for the string `web` at the beginning of a word.
- `C-M-s web\>`: Search for the string `web` at the end of a word.
- `C-M-s \<web.+server\>`: Search for the string `web` at the beginning of a word followed by one or more characters and the string `server` at the end of a word.
- `C-M-s \_<web.+server\_>`: Search for the string `web` at the beginning of a symbol followed by one or more characters and the string `server` at the end of a symbol.
- `C-M-s web\s server`: Search for the string `web` followed by one whitespace character and the string `server`.
- `C-M-s web\s-server`: Same as above.
- `C-M-s \s` : Search for whitespace character.
- `C-M-s \s-`: Same as above.
- `C-M-s \sw`: Search for word constituent character. Typically uppercase letters, lowercase letters and digits are considered word constituents.
- `C-M-s \s_`: Search for a symbol character that is used in variable names or command names.
- `C-M-s \s.`: Search for punctuation character.
- `C-M-s \s(`: Search for opening pair of a grouping character, e.g. `(`, `[`, `{`.
- `C-M-s \s)`: Search for closing pair of a grouping character, e.g. `)`, `]`, `}`, etc.
- `C-M-s \s"`: Search for string delimiter. This does not work in text mode but does work in programming modes.
- `C-M-s \s<`: Search for opening comment delimiter. This too does not work in text mode but does work in programming modes.
- `C-M-s \s>`: Search for closing comment delimiter. This too does not work in text mode but does work in programming modes.
- `C-M-s \Sw`: Search for character that is not a word constituent. The pattern `\S` matches any character whose syntax code is not the given syntax code (`w` in this example).

All examples above that contain the regular expression `\s` followed by a character matches a character that belongs to a specific syntax class. For example `\s.` matches characters that belong to the punctuation syntax class. The syntax class for each character is decided by the current major mode. Thus the same character may belong to different syntax classes in different modes. For example, while the character `#` belongs to the punctuation syntax class in text mode, it belongs to the comment syntax class in Python mode.

To find out which syntax class a particular character belongs to, place the cursor on the character and type `C-u C-x =`. The syntax field in the output buffer shows the syntax class of the character.

Here are some complete key sequences that demonstrate various search-and-replace features:

- `C-M-% \(web\)\(\s-\)\(server\) RET \3\2\1 RET`: Search for the string `web` followed by a whitespace and the string `server` and swap `web` with `server`.
- `C-M-% \(foo-\)\sw+\(-baz\) RET \1\?\2 RET`: Search for the string `foo-` followed by a word and the string `baz` and replace the middle word with text input provided by the user. Before each replace operation, Emacs will prompt the user to edit the replacement pattern by putting the point where `\?` was in the original replacement string.
- `C-M-% foo RET \# RET`: Search for the string `foo` and replace each match with an autoincrementing number. The first match is replaced with `0`, the second one with `1`, the third one with `2` and so on. Precisely speaking, the backreference `\#` refers to the count of the replacements already made in the current search and replace operation.
- `C-M-% foo RET \&\& RET`: Search for the string `foo` and duplicate it. The replacement pattern `\&` stands for the whole match.
- `C-M-% f.. RET \,(upcase \&) RET`: Search for the letter `f` followed by two characters and replace the match with an uppercase form of the match. The syntax `\,(form)` is used to evaluate an Elisp form and use its result in the replacement string. The backreference `\&` refers to the whole match as a string in the Elisp expression.
- `C-M-% [0-9]+ RET \,(+ 1000 \#&)`: Search for numbers and add 1000 to each match. The backreference `\#&` refers to the whole match as a number within the Elisp expression.
- `C-M-% \(\sw+\)-\(\sw+\) RET \,(upcase \2)-\1 RET`: Search for two words separated by a hyphen and then swap them but convert the second word in each match to uppercase. The backreference `\2` refers to the string matched by the second capturing group as a string within the Elisp expression.
- `C-M-% port-\([0-9]+\) RET port-\,(+ 1000 \#1) RET`: Search for the string `port-` followed by a number and add 1000 to the number. The backreference `\#1` refers to the string matched by the first capturing group as a string within the Elisp expression.

## Changing Case

Here are some commands to change case of text:

- `M-l`: Convert string from point to the end of word to lowercase.
- `M-u`: Convert string from point to the end of word to uppercase.
- `M-c`: Capitalise string from point to the end of word.
- `C-x C-l`: Convert region to lower case.
- `C-x C-u`: Convert region to upper case.
- `M-x upcase-initials-region RET`: Capitalise region.

Note that the commands `C-x C-l` (`downcase-region`) and `C-x C-u` (`upcase-region`) are disabled by default. Follow the prompts to try it or enable it. A quick way to try it is to type `SPC`. Also, adding the following to the Emacs initialisation file permanently enables it.

    (put 'downcase-region 'disabled nil)
    (put 'upcase-region 'disabled nil)

## Counting

Here are some commands to count lines, words, characters, patterns, etc:

- `M-=`: Count lines, words and characters in region.
- `M-x count-words-region RET`: Same as above.
- `M-x count-words RET`: Similar to above. If no region is selected, then counts in the entire buffer.
- `M-x how-many RET f.. RET`: Show the number of matches for the regular expression `f..` following point. If region is selected, then show the number of matches in the region.
- `M-x count-matches RET f.. RET`: Same as above.

## Deleting and Keeping Lines

The commands that are presented in this section can be tested with a buffer like this:

    foo
    bar

    foo
    bar

    foo
    foo

    bar
    foo

    baz
    baz
    baz

Here are the commands:

- `M-x delete-duplicate-lines RET`: Delete all but one copy of duplicate lines in region. When executed on the whole of the example buffer presented above, it leaves us with three non-empty lines and one blank line. When duplicate lines are encountered, the first instance of each line is kept intact and the others are deleted.
- `C-u M-x delete-duplicate-lines RET`: Like the previous command but search backwards. Thus effectively, the last instance of each repeated line is left intact while the other duplicates are deleted.
- `C-u C-u M-x delete-duplicate-lines RET`: Delete only those duplicate lines that are adjacent to each other. In every contiguous group of duplicate lines, the first one is left intact and the rest are deleted.
- `C-u C-u C-u M-x delete-duplicate-lines RET`: Like the first command in this list but repeated blank lines are left intact. When executed on the whole of the example buffer presented above, it leaves us with three non-empty lines and six blank lines.
- `M-x flush-lines RET b.. RET`: Delete lines in region that match the regular expression `b..`. If no region is active, then delete matching lines between the point and end of buffer. The deleted lines are not copied to kill ring.
- `M-x keep-lines RET b.. RET`: Keep lines in region that match the regular expression `b..` and delete the rest. If no region is active, then keep matching lines between the point and end of buffer and delete the rest. The deleted lines are not copied to kill ring.
- `M-x copy-matching-lines RET b.. RET`: Copy lines in region that match the regular expression `b..` to the kill ring. If no region is active, then copy matching lines between the point and end of buffer. (Available since Emacs 28.1)
- `M-x kill-matching-lines RET b.. RET`: Kill lines in region that match the regular expression `b..` to the kill ring. If no region is active, then kill matching lines between the point and end of buffer. (Available since Emacs 28.1)

To try each command on the entire buffer, first type `C-x h` to select the entire buffer as the region and then type a command mentioned above.

## Splitting and Joining Lines

Here is a list of commands that help with splitting and joining lines:

- `C-o`: Insert a newline after the point but do not move the point.
- `C-x C-o`: On blank line, delete all surrounding blank lines, leaving just one. On isolated blank line, delete the blank line. On non-blank line, delete all consecutive blank lines that follow the non-blank lines. While deleting blank lines it also deletes lines that consist only of whitespaces.
- `C-M-o`: Split current line at the next non-whitespace character after the point while maintaining its indentation. Everything from the next non-whitespace character after the point to the end of the line moves down by one line but the new line is indented so that the column numbers of all the characters that moved down remain the same. If a fill-prefix has been set, say with `C-x .`, then the fill-prefix is inserted in the new line.
- `M-^`: Join current line with previous line and leave exactly one space between the joined lines. If a fill-prefix is set, say with `C-x .`, then the fill-prefix is removed while joining lines.

The key sequence `C-x C-o` is very useful for removing spurious blank lines between paragraphs.

Note that `M-^` also works on a region. When a region is active, it joins all lines in the region.

## Examining and Fixing Whitespace Issues

Here is a list of commands that are useful in examining whitespace in the current buffer:

- `M-x whitespace-mode RET`: Toggle visualisation of spaces, tabs, newlines and lines longer than `whitespace-line-column` number of columns (80 by default) with special glyphs and colour.
- `M-x whitespace-newline-mode RET`: Toggle visualisation of newlines.
- `M-x whitespace-toggle-options RET`: Toggle local options for `whitespace-mode`.

After typing `M-x whitespace-toggle-options RET`, type a key to tell it what to do. For example, type `N` and it will start or restart `whitespace-mode` with the visualisation of newline toggled. Type `?` to see the list of all key inputs it supports.

The key sequence `M-x whitespace-toggle-options RET` may be typed anytime regardless of whether `whitespace-mode` is currently enabled or not. If `whitespace-mode` is not enabled, running `whitespace-toggle-options` automatically enables it. If `whitespace-mode` is already enabled, then running `whitespace-toggle-options` and toggling an option, restarts local `whitespace-mode` with the updated option setting.

Here are some commands to report and clean up whitespace issues:

- `M-x whitespace-report RET`: Shows a report of whitespace issues. The "Current setting" column on left shows the current settings found in the variable `whitespace-style`. The "Whitespace Problem" column on the right shows the whitespace problems found in the buffer.
- `M-x whitespace-report-region RET`: Like the previous command but reports problems in a region.
- `M-x whitespace-cleanup RET`: Cleans up whitespace issues in the buffer. This command checks the `whitespace-style` variable to decide which issues to fix. See `C-h f whitespace-cleanup RET` for complete details.
- `M-x whitespace-cleanup-region RET`: Cleans up whitespace issues in a region. Unlike the previous command, this command does not fix empty lines at the beginning or end of buffer. See `C-h f whitespace-cleanup-region RET` for complete details.

As mentioned in the list above, the whitespace cleanup functions read the variable `whitespace-style` to decide which whitespace issues to fix. Say, we do not want to fix trailing whitespace issue but do want to fix other whitespace issues selected by default (e.g. empty lines at the beginning or end of buffer, spaces before tab, etc.), then we need to update the `whitespace-style` variable as follows:

    (setq whitespace-style (delete 'trailing whitespace-style))

Now running `whitespace-cleanup` or `whitespace-cleanup-region` is going to skip fixing trailing spaces but it will perform the other cleanups determined by the value of `whitespace-style`.

## Keyboard Macros

The behaviour of keyboard macro key sequences depend on the current context. So they are presented as table below.

Key | Command | While not recording | While recording
--- | --- | --- | ---
`F3` | `kmacro-start-macro-or-insert-counter` | Start recording | Insert counter
`F4` | `kmacro-end-or-call-macro` | Call macro | End recording
`C-x (` | `kmacro-start-macro` | Start recording | Do nothing
`C-x )` | `kmacro-end-macro` | End recording | Do nothing
`C-x e` | `kmacro-end-and-call-macro` | Call macro | End recording and call macro

The key sequences in the table above can be divided into three groups:

- `C-x (` and `C-x )`: These invoke simple commands that start and stop macro recording.
- `F3` and `F3`: These are wrappers around the simple commands.
- `C-x e`: This is a slightly high level command too that wraps around simpler macro commands and functions that end recording and calls a macro.

Given these details, there are broadly two ways these macro key sequences can be used. They are shown in the table below.

Operation | Using Function Keys | Using Control Keys
--- | --- | ---
Start recording | `F3` | `C-x (`
Stop recording | `F4` | `C-x )`
Call macro | `F4` | `C-x e`
Stop recording and call macro | `F4 F4` | `C-x e`
Repeat call macro | `F4` | `e`

If you are comfortable using function keys, you might want to follow the second column in the table above. Otherwise, you might want to follow the third column in the table above.

The last row is not mentioned in the book but the fact that `e` may be used to repeat a macro call performed with `C-x e` is documented in the Emacs manual: Keyboard Macros: Basic Use.

Note that `F3` inserts a counter value and increments the counter value by 1 or by the number specified via a digit argument. Here is an example key sequence that may be typed in a buffer with multiple lines to demonstrate this:

1. Type `C-x (` to start macro recording.
2. Type `C-a F3 . SPC M-c C-n` to insert macro counter which `0` by default, followed by dot and space at the beginning of the line, capitalise the first word and move to the next line.
3. Type `C-x e` to stop macro recording and call the recorded macro. Now `1`, dot and space is inserted at the beginning of the line. The first word of the current line is capitalised and the cursor moves to the next line.
4. Type `e` to repeat the macro call. Keep typing `e` to repeat the macro call.

The behaviour of the the macro commands change with universal arguments and digit arguments as follows:

- `C-u F3`: Execute the last macro, then record new macro and append it to the last macro. Set `kmacro-execute-before-append` to `nil` (it is `t` by default) to prevent executing the last macro before appending a new macro to the last macro.
- `C-u C-x (`: Same as above.
- `C-5 F3`: Start recording but set counter to 5, i.e. while a macro is being recorded, typing `F3` inserts 5 the first time, 6 the second time and so on. The numeric prefix argument sets the counter value.
- `C-5 C-x (`: Same as above.
- `C-u F4`: Execute the second macro in the ring.
- `C-7 F4`: Repeat the last macro 7 times.
- `C-7 C-x e`: Repeat the last macro 7 times.
- `C-0 F3`: Repeat macro until there is an error (e.g. reaching the end of a buffer).
- `C-0 C-x e`: Same as above.

Type `C-x C-k C-h` to discover keyboard macro commands and their key bindings. The list below shows some of the interesting ones mentioned in the book. In the list below, complete key sequences are used, so that they serve as a demonstration of the macro commands.

- `C-x C-k C-a 20 RET`: Add 20 value to the counter.
- `C-x C-k TAB`: Insert counter. Note that we saw earlier that this can also be done with `F3`.
- `C-x C-k C-c`: Set counter.
- `C-x C-k C-f %02x`: Set macro counter format to zero-padded two-digit hexadecimal numbers with a minimum width of 2.

Note that all of the above commands work fine even when no macro recording is in progress. For example, earlier we saw that `F3` inserts the macro counter value only when a macro recording is in progress. However, `C-x C-k TAB` inserts the macro counter value even when a macro recording is not in progress.

Another interesting feature mentioned in the book is querying for user input while recording a keyboard macro. The key sequence to query the user is `C-x C-k q` or `C-x q`. Here are a few complete key sequences that may be used to demonstrate this feature:

- `F3 C-n C-a foo: C-x q C-e :bar F4`: This defines a macro such that when we execute the macro by typing `F4` one more time, the macro first inserts `foo` at the beginning of the next line, then it prompts us to decide if we want to continue with macro execution. If we type type `y`, then it continues with the remainder of the macro execution. If we type `n`, it skips the rest of the macro iteration and continue with the next iteration of the macro (such as when we are replaying the macro multiple times with a digit argument). If we type `RET`, it skips the rest of the macro execution as well as skip any further iterations of the macro (in case we are replaying the macro multiple times).
- `F3 C-a foo: C-x C-k q C-e :bar F4`: Same as above but slightly longer key sequence. The key sequence in the previous point is easier to remember and type.

In the above examples, when the macro playback prompts queries for user input, we can also type `C-l` to recentre the screen, `C-r` to enter recursive edit or `C-M-c` to exit recursive edit.

Note that the key sequence `C-l` behaves a little differently from the regular `C-l`. Unlike the regular `C-l`, successive invocations of this key sequence during macro query does not cause the window to reposition at various places (centre, top and bottom by default) in a cyclical order. Successive invocations of `C-l` during macro query, leaves the screen centred.

Here are some key sequences to save and recall macros:

- `C-x C-k C-p`: Move to the previous keyboard macro in the keyboard macro ring.
- `C-x C-k C-n`: Move to the next keyboard macro in the keyboard macro ring.
- `C-x C-k n foo RET`: Assign the name `foo` to the current keyboard macro in the keyboard macro ring. Now the macro can be executed by simply typing `M-x foo RET`.
- `M-x insert-kbd-macro foo RET`: Insert the definition of the named keyboard macro `foo` as Elisp code into the current buffer.
- `C-x C-k b C-c 1`: Assign the key sequence `C-c 1` to the current keyboard macro in the keyboard macro ring. Now the macro can be executed by simply typing `C-c 1`.

Finally, here are some commands to edit keyboard macros:

- `C-x C-k e C-x e`: Edit the current keyboard macro.
- `C-x C-k e M-x foo RET`: Edit the keyboard macro named `foo`.
- `C-x C-k e C-c 1`: Edit the keyboard macro bound to `C-c 1`.
- `C-x C-k l`: View the most recent 300 keystrokes and edit it to create a new keyboard macro.
- `M-x kmacro-edit-lossage RET`: Same as above.

A few additional commands:

- `C-h l`: See the last 300 characters typed (lossage).
- `M-x open-dribble-file foo.txt RET`: Write input events to a dribble file named `foo.txt`.
- `M-: (open-dribble-file nil) RET`: Close the dribble file.

## Text Expansion

### Abbrev

Here are some Abbrev commands:

- `C-x a l`: Take the word before the cursor and define a mode-specific abbreviation for it.
- `C-x a g`: Take the word before the cursor and define a global abbreviation for it.
- `C-x a i l`: Take the abbreviated word before the cursor and define a mode-specific expansion for it.
- `C-x a i l`: Take the abbreviated word before the cursor and define a global expansion for it.

Note that for the expansions to work Abbrev mode should be enabled, say with `M-x abbrev-mode RET`.

Here are some complete key sequences that demonstrate how we can use Abbrev to define an abbreviation, i.e. text that automatically gets replaced by another text:

- `Use SPC Debian C-x a l deb RET`: Define a mode-specific abbreviation `deb` such that whenever we type `deb`, it automatically expands to `Debian`.
- `Use SPC Linux C-x a g lnx RET`: Define a global abbreviation `lnx` such that whenever we type `lin`, it automatically expands to `Linux`.
- `Hello SPC wld C-x a i l World RET`: Define a mode-specific abbreviation `wld` such that whenever we type `wld`, it automatically expands to `World`.
- `Hello SPC evry C-x a i g Everyone RET`: Define a global abbreviation `evry` such that whenever we type `evry`, it automatically expands to `Everyone`.

Although not mentioned in the book, these commands can be used with a numeric prefix argument to specify the number of words before the cursor to be picked for expansion for the abbreviation we are about to define. Here are some complete key sequences that demonstrate this:

- `I use Debian GNU/Linux C-3 C-x a l dgl`: Define a mode-specific abbreviation `dgl` such that whenever we type `dgl`, it automatically expands to `Debian GNU/Linux`.
- `I use Debian GNU/Linux C-3 C-x a g dgl`: Similar to above but define a global abbreviation.

### DAbbrev

There are two key bindings discussed in the book:

- `M-/`: Expand the word just before the cursor to the nearest preceding word for which the current word is a prefix. If no suitable preceding word is found, expand it to the nearest succeeding word for which the current word is a prefix. Repeating this command cycles between the other matches found.
- `C-M-/`: Find all words in the buffer that has the current word before the cursor as the prefix and expand the current word to the longest common prefix of all these matching words. However, if the longest common prefix of the matching words is same as the word before the cursor, then present them as suggestions for completion. If there is exactly one matching word, expand the word before the cursor to that word.

The last command above takes a little while to get used to it. The following steps demonstrate how it works.

1. Create a text buffer with the following line:

       abacus apple appliance application

2. Type `ap` followed by `C-M-/`, the word expands to `appl` since that is the longest common prefix among the matching words.
3. Type `C-M-/` again. The matching words `apple`, `appliance` and `application` are presented as possible completions in a temporary buffer named `*Completions*`.
4. Now type `ic`, so that the word before the cursor becomes `applic` and type `C-M-/` again. Now the word before the cursor expands to `application` because that is the only possible completion now.

Note that by default DAbbrev looks for matching words in other open buffers too and offers them as completions.

### Hippie Expand

Unlike DAbbrev, Hippie Expand goes beyond open buffers to look for expansions. The variable `hippie-expand-try-functions-list` contains a list of expansion functions that `hippie-expand` uses to look for completions. The book suggests remapping `M-/` to invoke `hippie-expand` with this Elisp code:

    (global-set-key [remap dabbrev-expand] 'hippie-expand)

By default, Hippie Expand can complete file names, complete lines, etc. For example, if there is a line for which the current line is a prefix (leading whitespace is ignored while checking for matches), then the current line is expanded to the other matchine line.

Repeated invocations of this command cycles between the matches.

As mentioned earlier, the variable `hippie-expand-try-functions-list` determines which expansion algorithms are used. Here is an example that demonstrates how we can alter this variable:

    (setq hippie-expand-try-functions-list '(try-complete-lisp-symbol))

The above rather unrealistic example severely restricts the expansions Hippie Expand can perform. With the above example, word expansion, line expansion, file name completion, etc. are disabled. Only Elisp symbols are expanded. For example, typing `white` followed by `M-/` first expands the word to `whitespace` because all matching Elisp symbols have that as the longest common prefix. Typing `M-/` over and over again, completes the expansion further with various Elisp symbols.

As mentioned before, the above example is highly atypical. The above example is only meant for demonstrating how this variable can be set. Typically, users add more functions to this variable to add more expansion capabilities.

## Indenting

### Electric Indentation

Emacs automatically indents code as we type. The major mode decides the automatic indentation behaviour. The automatic identation is provided by a global minor mode named `electric-indent-mode` which is enabled by default.

### Indenting Current Line

Typing `TAB` indents the current line. In many modes like `emacs-lisp-mode`, `python-mode`, `text-mode`, etc. the command `indent-for-tab-command` is bound to it. But there are modes that bind another command to `TAB`. For example, in `c-mode`, the command `c-indent-line-or-region` is bound to `TAB`.

The behaviour of `indent-for-tab-command` is determined by the variables `tab-always-indent`. It is `t` by default which causes `TAB` to just indent the current line. If set to `nil`, hitting `TAB` indents the current line only if the point is before the first non-whitespace character of the line. Otherwise it inserts tabs or spaces to move the point to the next tab stop column. If set to `'complete`, typing `TAB` first tries to indent the current line but if the line is already correctly indented, then it tries to complete the thing at point.

When `indent-for-tab-command` is bound to `TAB` and when `indent-for-tab-command` decides to indent the current line, it calls the function in the variable `indent-line-function` to perform the indentation. Here is a table that shows what `indent-line-function` contains in a few major modes where `indent-for-tab-command` command is bound to `TAB`:

`major-mode` | `indent-line-function`
--- | ---
`emacs-lisp-mode` | `lisp-indent-line`
`python-mode` | `python-indent-line-function`
`text-mode` | `indent-relative`

While `lisp-indent-line` and `python-indent-line` attempt to indent the current line according to the syntax of the language, `indent-relative` inserts tabs and spaces to move the point to the next indentation point where the indentation point is defined as the next non-whitespace character following whitespace. This can be useful in aligning the point with words in the previous line. If the previous line has no indentation point (e.g. the previous line is an empty line or does not have whitespace), then `tab-to-tab-stop` is invoked which inserts tabs or spaces to move the point to the next tab stop column.

The command `tab-to-tab-stop` command introduced in the previous paragraph can also be invoked with `M-i`.

### Use Only Spaces for Indentation

By default, Emacs uses a mix of tabs and spaces for indentation and alignment. When it needs to align the first non-whitespace character of a line with a certain token in the previous line, it would insert as many tabs as it can followed by a few spaces if necessary to attain the desired alignment. To force Emacs to always use spaces for indentation and alignment, add the following Elisp code to the Emacs initialisation file:

    (setq-default indent-tabs-mode nil)

### Tab Width

The variable `tab-width` is used in various contexts while performing indentation and alignment. For example, when `indent-tabs-mode` is enabled, for every `tab-width` columns of indentation required, Emacs inserts a tab to indent the code.

Also, when `indent-tabs-mode` is set to `nil`, typing `M-i` inserts as many spaces as necessary to move the point to the next tab stop column where the distance between two tab stops is assumed to be `tab-width`.

### Edit Tab Stops

The behaviour of `M-i` can be customised further by manually defining tab stop columns. Type `M-x edit-tab-stops RET` first. A buffer named `*Tab Stops*` appears. The second and third line of this buffer contains a ruler to indicate the column numbers. Type `:` (i.e. colon) in the first line whereever you want to define tab stops. Then type `C-c C-c` to install the changes. Now when `M-i` is typed in a text buffer, each time it inserts as many tabs (if `indent-tabs-mode` is `t`) or spaces as necessary to move the point to the next tab stop column as defined earlier in the `*Tab Stops*` buffer.

### Indent Region

Typing `TAB` when a region is active indents the region according to the major mode's indentation rules. It invokes the same command as the one invoked when we type `TAB` to indent a line. The command bound to it takes care of indenting region. For example, if `TAB` is bound to `indent-for-tab-command`, the latter checks if a region is active and if it is, then it simply calls `indent-region`.

The `indent-region` command can be invoked explicitly using `C-M-\`. If `fill-prefix` has been set, say with `C-x .`, then it is added to every line in the region being indented. With a numeric prefix argument, each line in the region is indented to the column indicated by the argument. For example, `C-M-1 C-M-0 C-M-\` indents each line of the region to column 10.

### Indent Rigidly

When we want to rigidly control how a region must be indented, we can type `C-x TAB` to perform rigid indentation. Doing so allows us to bypass the indentation rules of the major mode. Instead we control exactly how the indentation must be done. The following complete key sequences demonstrates a few examples of rigid indentation:

- `C-x TAB`: Interactively indent region. Type `<right>` or `<left>` to increase or decrease indentation by one space respectively. Type `<right>` or `<left>` to increase or decrease indentation by one tab stop respectively.
- `C-6 C-x TAB`: Indent region by 6 spaces. Appropriate number of tabs and spaces are inserted to achieve an apparent 6 spaces of indentation. Whether tabs are inserted or not and how many tabs are inserted depend on the values of `indent-tabs-mode` and `tab-width` as explained in the previous sections.
- `C-- C-6 C-x TAB`: Reduce indentation of region by 6 spaces.

## Sorting

Assuming a region is active, here are some complete key sequences for various sorting commands:

- `M-x sort-lines RET`: Sort lines alphabetically.
- `C-u M-x sort-lines RET`: Reverse sort lines alphabetically.
- `M-x sort-fields RET`: Sort lines alphabetically by the first field alphabetically. Fields are separated by whitespace.
- `M-2 M-x sort-fields RET`: Sort lines alphabetically by the second field.
- `M-2 M-x sort-numeric-fields RET`: Sort lines numerically by the second field.
- `M-x sort-columns RET`: Sort columns between the column position of mark and column position of point.
- `M-x sort-regexp-fields RET [A-Z]*->\(.*\) RET \1 RET`: Sort the strings in each line matched by the given regular expression by the field matched by the first (and the only) capturing group in the regular expression. The part of each line that is not matched by the regular expression remains intact. They never move. Only the part of each line that is matched by the regular expression moves around during the sorting operation.
- `M-x sort-regexp-fields RET`: Sort paragraphs alphabetically.

## Aligning

The two simple commands for aligning text introduced first in the book are:

- `M-x align RET`: Aligns current region.
- `M-x align-current RET`: Aligns current section. A section is a group of consecutive lines both below, above and including the current line for which the first alignment rule (according to the major mode) applies.

Consider the following Elisp buffer:

    (defvar person '(("name" . "Alice")
                     ("city" . "London")
                     ("country" . "UK")))

If we type `C-x h` followed by `M-x align RET` or if we put the cursor on any line of the above code and type `M-x align-current RET`, we get the following result:

    (defvar alice '(("name"    . "Alice")
                    ("city"    . "London")
                    ("country" . "UK")))

There is also an `align-regexp` command that allows us to parts of lines by regular expressions. The following experiments demonstrate this command.

1. First create a buffer with the following text:

       Alice:London:UK
       Bob:Paris:France
       Carol:Tokyo:Japan

2. Type `C-x h` followed by `C-u M-x align-regexp \(\s-*\): RET 1 RET 1 RET y RET`. The result looks like this:

       Alice :London :UK
       Bob   :Paris  :France
       Carol :Tokyo  :Japan

   Note that the regular expression capturing group `\(\s-*\)` appears as the default in the minibuffer. We only add `:` to it. Similarly the two occurrences of `1` appear as default values. The first `1` is the default for determining which parenthesis group to modify. The second `1` is the default for amount of spacing to be used during alignment. The `y` in the end specifies that we want to repeat the alignment throughout the line.

3. Type `C-/` to undo the changes done in the last step. Then type `C-x h` followed by `M-x align-regexp : RET`. This is a shorter equivalent to the previous command. The output is same as before.

4. Type `C-/` to undo the changes done in the last step. Then type `C-x h` followed by `C-u M-x align-regexp :\(\s-*\) RET 1 RET 1 y RET`. Note that the only difference this time is that we place the colon before the parenthesis group. The result looks like this:

       Alice: London: UK
       Bob:   Paris:  France
       Carol: Tokyo:  Japan

5. Type `C-/` to undo the changes done in the last step. Then type `C-x h` followed by `C-u M-x align-regexp \(\s-*\): RET 1 RET 0 y RET`. Note that the only difference this time is that we place the colon before the parenthesis group. We specify `0` as the amount of spacing this time, so a minimum of zero spacing is used for alignment when possible. The result looks like the following. Notice the lack of space after `Alice` and `Carol`.

       Alice:London:UK
       Bob  :Paris :France
       Carol:Tokyo :Japan

6. Type `C-/` to undo the changes done in the last step. Then type `C-x h` followed by `C-u M-x align-regexp \(\s-*\): RET 1 RET 5 y RET`. Note that the only difference this time is that we place the colon before the parenthesis group. We specify `5` as the amount of spacing this time, so a minimum of 5 spaces are used for alignment.

       Alice     :London     :UK
       Bob       :Paris      :France
       Carol     :Tokyo      :Japan

## Zap to Char

The steps below demonstrate the `zap-to-char` command that is bound to the key sequence `M-z`. This command kills up to and including the given character.

1. Create a buffer with the following text:

       foo bar baz qux quux

2. Type `M-<` to go to the beginning of the buffer and then type `M-z r` to kill text up to and including the first occurrence of the letter `r`. The buffer now looks like this:

         baz qux quux

3. Type `M-<` to go to the beginning of the buffer and then type `M-z x` to kill text up to and including the first occurrence of the letter `x`. The buffer now looks like this:

        quux

4. Now type `C-e SPC C-y` to reinsert the killed text at the end of the line. The buffer now looks like this:

        quux foo bar baz qux

   Note that the last step yanks both chunks of text that were killed in the previous two steps. This is due to the fact that consecutive kills append to the same stretch of text in the kill ring. This fact was discussed earlier in section Append Kill

5. Now type `M-<` to go back to the beginning of the buffer again. Then type `M-2 M-z a`. The numeric argument `2` specifies that we want to zap up to the second occurrence of the letter `a`. The buffer looks like this:

       z qux

6. Type `C-e SPC C-y` to reinsert the text killed in the previous step at the end of the line. The buffer looks like this now:

       z qux quux foo bar ba

7. Type `M-- M-2 M-z x` to zap backward up to the second occurrence of the letter `x`. The buffer looks like this now:

       z qu

## Zap up to Char

Here are some steps that demonstrate the `zap-up-to-char` command. This command kills text up to, but not including, the given character.

1. Create a buffer with the following text:

       foo bar baz qux quux

2. Type `M-<` to go to the beginning of the buffer. Then type `M-x zap-up-to-char RET b`. The result now looks like this:

       bar baz qux quux

3. Type `M-2 M-x zap-up-to-char RET q`. The result now looks like this:

       quux

4. Type `C-e SPC C-y` to reinsert the killed text at the end of the buffer:

       quux foo bar baz qux

5. Type `M-- M-2 M-x zap-up-to-char RET b`. The buffer now looks like this:

       quux foo b

The author of the book suggests binding this command to `M-S-z` with the following Elisp code:

    (global-set-key (kbd "M-S-z") 'zap-up-to-char)

The above code, however, does not create the binding successfully. Therefore, use the following Elisp code instead:

    (global-set-key (kbd "M-Z") 'zap-up-to-char)

Now the commands presented in this section above can be typed as follows:

- `M-Z b`
- `M-2 M-Z q`
- `M-- M-Z b`

## Spell Check

The spell checking commands of Emacs require a spell checking program to be installed on the system. Emacs supports the spell checking programs `aspell`, `ispell`, `hunspell` and `enchant-2`. If multiple programs are present, it looks for them one by one in the order specified in the previous sentence and picks the first one that is found. The following spell checking commands are introduced in the book:

- `M-$`: Check spelling of word under or before the cursor. Possible corrections are offered in a new window. If the word under or before the cursor is already correct, a message like `APPLE is correct` appears in the echo area. When corrections are offered, each correction is numbered. Type `SPC` to leave the word unchanged or type a number to choose a numbered correction. Type `x` to exit the the spelling buffer (the one that shows corrections). Type `q` to quit the spelling session (kills the spelling program process). To see the list of all key bindings supported, type `C-h f ispell-help RET`.
- `M-x flyspell-mode RET`: Toggle on-the-fly spell checking. Misspelled words are underlined with squiggly lines. Type `C-M-i` or `C-.` to correct a misspelled word under or before the cursor. All possible corrections appear in the echo area. Repeat `C-M-i` or `C-.` to cycle through the possible corrections.
- `M-x flyspell-prog-mode RET`: Turns on `flyspell-mode` for comments and strings only. This is useful while working in a buffer with a programming mode enabled.
- `M-x ispell-buffer RET`: Check the current buffer for spelling errors interactively. Each misspelled word is highlighted and corrections are offered in a new window. The interface and key sequences for making corrections are the same as the ones for `M-$` introduced above.
- `M-x ispell-region RET`: Like the previous command but checks the current region for spelling errors.

## Dictionary Lookup

The following complete key sequences demonstrate some of the dictionary commands introduced in the book:

- `M-x dictionary-lookup-definition RET`: Look up definitions of the word at or before the cursor.
- `M-x dictionary-search RET programming RET`: Search definitions of the word `programming`.
- `M-x dictionary-select-dictionary RET`: This command presents a list of available dictionaries in a new buffer. Navigate the buffer and click on a dictionary or type `RET` while the cursor is on a dictionary entry to select it. For example, move the cursor down to the entry that begins with the text `jargon:` and type `RET` and then type `M-x dictionary-search RET programming RET` to see the definition of the word `programming` from the Jargon File only.

The dictionary commands first attempt to connect to a locally running dictionary server. If the connection does not succeed, it prompts for consent to connect to dict.org. Typing `y` at the prompt allows the command to proceed and complete the command.

## Quoted Insert

Here are some complete key sequences that demonstrate quoted insert:

- `C-q C-l`: Insert form feed character. This is displayed as `^L` in Emacs using the face named `escape-glyph`. Emacs treats each form feed character as a page break and we can navigate back and forth between pages with `C-x [` and `C-x ]` respectively.
- `C-q (`: Insert a literal open parenthesis. Useful in `paredit-mode` where the key sequence `(` is bound to `paredit-open-round` which inserts a balanced pair of parentheses. To insert a single parenthesis instead, we can perform a quoted insert with `C-q (`.
- `C-q TAB`: Insert a literal tab character.
- `C-q C-j`: Insert a literal line feed character, i.e. a newline character.
- `C-q RET`: Insert a literal carriage return. This is displayed as `^M` in Emacs.
- `C-q ESC`: Insert a literal escape character. This is displayed as `^[` in Emacs.
- `C-q C-[`: Same as above.

## Links

The following list includes some links that were discussed during the book discussion group meetings:

- Aspell and Hunspell: A Tale of Two Spell Checkers
- Spell checkers in Emacs in 2020