就上下文而言,我是一个 emacs 新手。我使用它的时间不长,但使用得越来越多(我非常喜欢它)。另外,我对 lisp 很熟悉,但对 elisp 不太熟悉。

我需要做的是将正则表达式绑定到键盘组合,因为我经常使用这个特定的正则表达式。

我一直在做什么:

M-C-s ^.*Table\(\(.*\n\)*?GO\)

注意,我在上面使用了换行符,但我发现 isearch-forward-regexp, ,你确实需要更换 \n 在正则表达式中,结果为 C-q Q-j. 。这会插入一个文字换行符(不结束命令),使我能够将换行符放入表达式中并进行跨行匹配。

如何将其绑定到组合键?

我隐约明白我需要创建一个执行的 elisp 函数 isearch-forward-regexp 表达了,但我对细节很模糊。我搜索过谷歌,发现大多数文档都有点令人困惑。

如何将正则表达式绑定到 emacs 中的组合键?


到目前为止,迈克·斯通给出了最好的答案——不是 确切地 我正在寻找什么,但它满足了我的需要

编辑-这种方法有效,但是在存储宏之后,当我稍后回去使用它时,我无法将它与 C-x e. 。(即,如果我重新启动 emacs 然后输入 M-x 宏名称, , 进而 C-x e, ,我在迷你缓冲区中收到一条消息,例如“没有最后一个 kbd 宏”或类似的消息)


@Mike Stone - 感谢您提供的信息。我尝试创建一个宏,如下所示:

C-x( M-C-s ^.*Table\(\(.*C-q C-J\)*?GO\) C-x)

这创建了我的宏,但是当我执行宏时,我没有得到与我使用时通常得到的相同的突出显示 isearch-forward-regexp. 。相反,它只是跳到表达式的下一个匹配的末尾。所以这并不能真正满足我的需要。有任何想法吗?

编辑:看来我 使用宏来做我想做的事,我只需要跳出框框思考 isearch-forward-regexp. 。我会尝试你的建议。

有帮助吗?

解决方案

你可以使用宏,只需这样做 C-x ( 然后为宏做所有事情,然后 C-x) 结束宏,然后 C-x e 将执行最后定义的宏。然后,您可以使用它来命名它 M-x 名称-最后-kbd-宏 它允许您为其分配一个名称,然后您可以使用它来调用 M-x 测试, ,然后使用存储定义 M-x 插入 kbd 宏 这会将宏放入当前缓冲区,然后您可以将其存储在您的 .emacs 文件。

例子:

C-x( abc *return* C-x)

将定义一个宏来输入“abc”并按回车键。

C-xeee

立即执行上述宏 3 次(第一个 e 执行它,然后后面的 2 个 e 将再执行两次)。

M-x name-last-kbd-macro testit

将宏命名为“testit”

M-x testit

执行刚刚命名的宏(打印“abc”然后返回)。

M-x insert-kbd-macro

将以下内容放入当前缓冲区中:

(fset 'testit
   [?a ?b ?c return])

然后可以将其保存在您的 .emacs 文件以在重新启动 emacs 后一遍又一遍地使用指定的宏。

其他提示

我已经开始从字面上解决你的问题,

(defun search-maker (s)
  `(lambda ()
     (interactive)
     (let ((regexp-search-ring (cons ,s regexp-search-ring)) ;add regexp to history
           (isearch-mode-map (copy-keymap isearch-mode-map)))
       (define-key isearch-mode-map (vector last-command-event) 'isearch-repeat-forward) ;make last key repeat
       (isearch-forward-regexp)))) ;`

(global-set-key (kbd "C-. t") (search-maker "^.*Table\\(\\(.*\\n\\)*?GO\\)"))
(global-set-key (kbd "<f6>") (search-maker "HELLO WORLD"))

键盘顺序来自 (kbd ...) 开始新的空白搜索。要实际搜索您的字符串,请按 最后一个键 根据需要重复多次。所以 C-. t t t 或者 <f6> <f6> <f6>. 。该解决方案基本上是一个 hack,但如果您想尝试一下,我会将其留在这里。

以下可能是最接近您需要的,

(defmacro define-isearch-yank (key string)
  `(define-key isearch-mode-map ,key 
     (lambda ()
       (interactive) 
       (isearch-yank-string ,string)))) ;`

(define-isearch-yank (kbd "C-. t") "^.*Table\\(\\(.*\\n\\)*?GO\\)")
(define-isearch-yank (kbd "<f6>") "HELLO WORLD")

组合键现在仅在 isearch 模式下有效。您正常开始搜索,然后按组合键插入预定义的字符串。

@贾斯汀:

执行宏时,有点不同......增量搜索只会发生一次,如果要再次搜索,则必须再次执行宏。不过,您可以做更强大和复杂的事情,例如搜索关键字,跳转到行首,标记,转到行尾,M-w(复制),然后跳转到另一个缓冲区,然后 C-y(粘贴),然后跳回另一个缓冲区并结束宏。然后,每次执行宏时,您都会将一行复制到下一个缓冲区。

emacs 宏最酷的一点是它会在看到铃声时停止......当您无法匹配增量搜索(除其他外)时,就会发生这种情况。所以上面的宏,你可以执行 C-u 1000 C-x e 这将执行宏 1000 次......但既然您进行了搜索,它只会复制 1000 行,或者直到搜索失败!这意味着如果有 100 个匹配项,则只会执行宏 100 次。

编辑:查看 C-hfhighlight-lines-matching-regexp 它将显示一个命令的帮助,该命令突出显示与正则表达式匹配的所有内容...我不知道如何撤消突出显示...无论如何,您可以使用存储的宏来突出显示所有匹配正则表达式的内容,然后使用另一个宏来查找下一个...?

进一步编辑:M-x unhighlight-regexp 将撤消突出显示,但您必须输入最后一个正则表达式(但它默认为您用于突出显示的正则表达式)

一般来说,要在 Emacs 中定义自定义键绑定,您可以编写

(define-key global-map (kbd "C-c C-f") 'function-name)

define-key 不出所料,它是定义新键的函数。 global-map 是全局键盘映射,而不是每种模式的单独映射。 (kbd "C-c C-f") 返回表示按键序列的字符串 C-c C-f. 。还有其他方法可以做到这一点,包括直接输入字符串,但这通常是最直接的,因为它采用正常的书面表示形式。 'function-name 是一个符号,表示函数的名称。

现在,除非您的函数已经定义,否则您需要在使用它之前定义它。为此,请写

(defun function-name (args)
  (interactive)
  stuff
  ...)

defun 定义一个函数——使用 C-h f defun 了解更多具体信息。这 (interactive) 并没有真正的函数调用;它告诉编译器用户可以使用以下命令调用该函数 M-x function-name 并通过键绑定。

现在,特别是对于交互式搜索,这是很棘手的;这 isearch 模块似乎并没有真正针对您想要做的事情进行设置。但你可以用它来做类似的事情。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top