Câu hỏi Giết bộ đệm có tên bắt đầu bằng một chuỗi cụ thể


Đây là vấn đề của tôi: Tôi sử dụng Emacs và nhận được rất nhiều bộ đệm khá vô dụng mọi lúc, như * Tin nhắn * hoặc * Số lần hoàn thành *.

Tôi muốn liên kết \ C-y để đóng tất cả các bộ đệm bắt đầu bằng * ngoại trừ các bộ đệm * shell * (và * shell * <k>).

Để làm điều đó, tôi muốn thêm một số Emacs-Lisp trong tập tin .emacs của tôi:

(defun string-prefix s1 s2
  (if (> (string-length s1) (string-length s2)) nil
    (string=? s1 (substring s2 0 (string-length s1))) ))

(defun curry2
  (lambda (f)
    (lambda (x)
      (lambda (y)
    (f x y) ))))

(defun filter
  (lambda (f l)
    (if (null? l) '()
      (let ((rest (cdr l)))
    (if (f (car l)) (cons (car l) rest)
      rest) ))))


(defun kill-useless (arg)
  (interactive "p")
  (map 'kill-buffer
       (filter
    (not ((curry2 string-prefix) "*shell*"))
    (list-buffers)
    ) ))

(global-set-key "\C-y" 'kill-useless)

Tôi đã thử nghiệm string-prefix và curry2 sử dụng Đề án và filter có vẻ khá đơn giản. Đáng buồn là tôi không thể kill-useless để hoạt động bình thường.

Nó nói rằng filter: Invalid function: (curry2 string-prefix).

Bây giờ, vấn đề là tôi có thể hút Emacs-Lisp, tôi không thực sự sử dụng bất kỳ Lisp nào ngoại trừ Scheme, và trong Scheme (MIT), nó hoạt động:

(filter ((curry2 string-prefix?) "*shell") '("*shell*" "*sh22" "eel"))
;Value 5: ("*shell*")

Tôi muốn:

  1. một cách để sửa mã của tôi
  2. các đề xuất về cách thực hiện điều này theo một cách khác

Cảm ơn!


13
2018-02-23 21:44


gốc


Các *Message* đệm là một hữu ích: mỗi khi Emacs cho bạn biết một cái gì đó, nó để cho nó ở đó, vì vậy bạn có thể ví dụ sao chép và dán nó vào google để tìm một giải pháp trên google. Hãy cẩn thận cũng là khi bạn có thể sẽ sử dụng một số chế độ (như magit), những người sẽ sử dụng bộ đệm như vậy một cách hữu ích. - Rémi
Có, tôi đã kết thúc việc giữ bộ đệm đó. Cảm ơn vì tiền hỗ trợ! - Dan Filimon


Các câu trả lời:


Một cách tiếp cận thay thế:

(require 'cl)

(defun is-useless-buffer (buffer)
  (let ((name (buffer-name buffer)))
    (and (= ?* (aref name 0))
         (not (string-match "^\\*shell\\*" name)))))

(defun kill-useless-buffers ()
  (interactive)
  (loop for buffer being the buffers
        do (and (is-useless-buffer buffer) (kill-buffer buffer))))

12
2018-02-23 22:42



1 cho vòng lặp trên bộ đệm xây dựng. Tốt đẹp! - ataylor
Tôi thích cách tiếp cận này nhiều nhất. Tôi cũng đã thêm vào một kiểm tra để giữ bộ đệm * Tin nhắn *. Chúc mừng Sean! Bạn giành chiến thắng :) Ngoài ra, những gì hiện (require 'cl) làm chính xác? - Dan Filimon
Nó mang đến gói Common Lisp của Emacs, đó là nơi mà macro (vòng lặp cực kỳ tiện dụng) "sống". Toàn bộ gói là rất hữu ích; dòng đầu tiên trong tệp .emacs của tôi là (yêu cầu 'cl). Xem gnu.org/software/emacs/manual/html_mono/cl.html - Sean


C-h  f  kill-matching-buffers  RET

kill-matching-buffer là một hàm Lisp được biên dịch tương tác trong   `files.el '.

(kill-matching-buffer REGEXP & tùy chọn INTERNAL-TOO)

Giết bộ đệm có tên khớp với REGEXP được chỉ định.   Đối số thứ hai tùy chọn cho biết có nên xóa bộ đệm nội bộ hay không.


26
2018-02-23 22:37



1 cho chức năng tích hợp mặc dù một ví dụ thực tế về cách sử dụng nó sẽ hữu ích hơn rất nhiều. - Dan Filimon
Nó tiếp tục hỏi nếu tôi muốn đóng mọi bộ đệm mặc dù (ngay cả khi chưa sửa đổi) - có cách nào để tránh điều đó không? - Zitrax
Zitrax: stackoverflow.com/a/10931190/324105 - phils
Vâng, giao diện người dùng của chức năng đó thực sự là xấu. Trong một hiệu ứng bắt đầu nhấn y thực sự nhanh chóng và khi một đã sửa đổi bộ đệm cho thấy bạn đã giết nó trước khi nhận thấy câu hỏi hơi khác một chút ... - olejorgenb


Hãy ghi nhớ elisp không phải là chương trình, hoặc thậm chí phổ biến lisp. Cú pháp và ngữ nghĩa khác nhau. Ví dụ, defun yêu cầu một danh sách tham số được bao quanh bởi dấu ngoặc đơn. Ngoài ra, currying là không thực sự có thể trong elisp.

May mắn thay, elisp đã xây dựng cho hầu hết những gì bạn muốn làm. Dành cho string-prefix bạn có thể dùng string-prefix-p được xây dựng trong. Dành cho filter, bạn có thể dùng remove-if-not, hoặc là remove-if cho nghịch đảo.

Đối với cà ri bạn có thể sử dụng apply-partially Hàm dựng sẵn. Để có được một hàm phù hợp với các chuỗi với tiền tố "*shell*", hãy thử một cái gì đó như thế này:

(apply-partially 'string-prefix-p "*shell*")

Bạn có thể sử dụng nó như thế này:

(mapcar
 (apply-partially 'string-prefix-p "*shell*")
 '("*shell*" "foo" "*shell*<2>"))

; results in
(t nil t)

(require 'cl) ; for remove-if
(remove-if
 (apply-partially 'string-prefix-p "*shell*")
 '("*shell*" "foo" "*shell*<2>"))

; results in
("foo")

5
2018-02-23 22:30



Cảm ơn những người đứng đầu, nhưng tôi đã cho câu trả lời cho người đã đưa cho tôi một giải pháp làm việc. Cố gắng để tìm hiểu về công việc này sẽ không có quá nhiều niềm vui! - Dan Filimon


Nó có thể là một ý tưởng tốt để xem những gì bạn sẽ xóa trước khi xóa nó, để chơi an toàn.

Trong Icicles, theo mặc định C-x k là một lệnh đa mà bạn có thể sử dụng để giết bất kỳ số lượng bộ đệm nào phù hợp với đầu vào minibuffer của bạn. Trong trường hợp này, bạn sẽ nhập * TAB để xem tất cả các tên đệm bắt đầu bằng * là ứng cử viên hoàn thành.

Sau đó, bạn có thể thu hẹp các kết quả phù hợp theo nhiều cách. Khi tất cả các trận đấu còn lại là những gì bạn muốn, nhấn C-! để xóa tất cả các bộ đệm đó.

Trong trường hợp bạn trình bày, bạn không muốn xóa bộ đệm có tên *shell.... Vì vậy, sau * TAB bạn sẽ đánh S-SPC và sau đó nhập một mẫu khác để khớp: shell, sau đó S-TAB. Điều đó chỉ thu hẹp lại *shell... bộ đệm mà bạn làm không phải muốn giết. Sau đó bạn nhấn C-~ để trừ các kết quả phù hợp (bổ sung). Điều đó để lại tất cả các vùng đệm ngoại trừ vùng đệm. Đánh C-! và tất cả họ đều bị giết.

Bạn cũng có thể giết từng bộ đệm bằng cách chỉ cần nhấp vào tên của chúng trong việc kiểm soát *Completions*: C-mouse-2.

Nói chung, trong Icicles  mỗi lệnh đa đọc tên đệm cho phép bạn sử dụng S-delete (Shift + phím Delete) để xóa các ứng cử viên đệm.

http://www.emacswiki.org/emacs/Icicles_-_Multi-Commands

http://www.emacswiki.org/emacs/Icicles_-_More_About_Multi-Commands


0
2017-08-20 15:28





tôi đã tìm thấy kill-matching-functions nhắc tôi cho bộ đệm chưa sửa đổi, không phải là những gì tôi muốn. Hàm bên dưới sẽ giết các bộ đệm khớp với một tiền tố (như trong tiêu đề của câu hỏi). Không chính xác những gì bạn muốn, nhưng có lẽ những người như tôi đến đây từ Google sẽ thấy điều này hữu ích.

(require 'cl)
(defun kill-buffers-with-prefix (prefix)
  "Kill buffers whose names start with the given prefix"
  (interactive "sPrefix to kill: ")
  (loop for buffer in (buffer-list)
        do (if (string-prefix-p prefix (buffer-name buffer))
               (kill-buffer buffer))))

0
2017-11-19 19:37





Để giết tất cả các bộ đệm khác

(defun px-kill-other-buffers ()
  "Kill all other buffers."
  (interactive)
  (mapc 'kill-buffer (delq (current-buffer) (buffer-list))))

Để tìm kiếm đầu chuỗi

(defun string-starts-with-p (string prefix)
    "Return t if STRING starts with prefix."
    (and
     (string-match (rx-to-string `(: bos ,prefix) t) string)
     t))

0
2017-08-23 13:08