剑神一笑

怎样的心情

用户操作
[即时聊天] [发私信] [加为好友]
剑神一笑ID:pankun
32659次访问,排名3591好友0人,关注者4
pankun的文章
原创 27 篇
翻译 0 篇
转载 1 篇
评论 72 篇
剑神一笑的公告
剑神一笑 男 24 四川人

现客居广州

关注编译器开发,动态语言编译器优化,高性能网络服务器开发,逆向工程

最近评论
bakkill:虽然不太明白!但还要感谢楼主,希望多发些交流学习之用的好帖子!!
ZeroChou:谁说汇编要被淘汰了? 看看你现在用的盗版软件有几个破解过程跟汇编无关的? 看看你中的超级病毒有几个没用到汇编!
rawa459:我也在开发一个编译器。
欢迎访问http://rawapyin.blog.sohu.com
unwritewolf:呵呵
关注!!!
Nocky:我恰巧也写了一篇关于C++模拟C#的属性机制的文章,写完之后找到了你这篇,刚好方法不一样,要以一起讨论下一,在下拙作URL:
http://tiannocky.spaces.live.com/default.aspx
文章分类
收藏
相册
朋友
风焱
framesniper
Skywind
大宝
老李
蓝色光芒
龙子龙孙
我的作品
Pascal编译器
外挂与反外挂
要反复看的书
编译原理 技术与工具
计算机程序的构造和解释
设计模式
存档
软件项目交易
订阅我的博客
XML聚合  FeedSky
订阅到鲜果
订阅到Google
订阅到抓虾
订阅到BlogLines
订阅到Yahoo
订阅到GouGou
订阅到飞鸽
订阅到Rojo
订阅到newsgator
订阅到netvibes

原创 一个emacs扩展,从指定目录或文件中搜索指定关键字收藏

 | 旧一篇: 放弃,才有所得。

    这段时间在熟悉一套系统的代码,经常要查找某个变量或函数名在哪些文件中被引用到了 ,虽然在linux下面grep一下就行了,但要查看每处的上下文,还是得打开文件.还好用的是emacs,有什么不爽就自己扩展
    刚用elisp时倒郁闷了一把,elisp貌视不支持尾递归(??还需查证) ,我一上来就用在scheme中惯用的过程自调用的方式来进行递归查找目录中的文件,结果很轻易就会超过elisp的最大求值嵌套深度,改为用elisp中的while则正常.
   实现了search-direct和search-file二个函数,分别是查找指定目录和指定文件,查找结果会加上文件名和行号,内容在结果窗口显示,在结果行上回车则会自动打开相应文件并跳到相应行.不足还有很多,忙过这段时间再扩展了 :-)   保存下面的代码自己本地目录,再在.emacs中添加(require 'file-search) 就可以了
效果图:



file-search.el


;;; file-search.el

(defconst fs-file-search-buffer-name "*file-search*")

(defvar fs-file-list-length 0)
(defvar fs-file-search-str "")
(defvar fs-match-regexp "")
(defvar fs-file-search-keymap (make-sparse-keymap))
(define-key fs-file-search-keymap (kbd "RET") 'fs-result-choose)

(defface fs-file-name-face '((t (:foreground "red" :bold t :underline t)))
  "Face used to highlight the file name")
(defface fs-line-face '((t (:foreground "green" :bold nil :underline nil)))
  "Face used to highlight the line number")

;;查找列表中所有文件
(defun fs-search-list-file (list)
  (while list
    (let ((file-name (car list)))
      (if (not (file-accessible-directory-p file-name))
          (progn
            (message "current file:%s %d in %d"
                     file-name
                     ( + (- fs-file-list-length (length list)) 1)
                     fs-file-list-length)
            (fs-search-file file-name 1))))
    (setq list (cdr list))))

;;查找指定目录
(defun fs-search-directory (dir-name)
  (if (file-accessible-directory-p dir-name)
      (let ((list (cdr (cdr (directory-files dir-name t fs-match-regexp)))))
        (setq fs-file-list-length (length list))
        (fs-search-list-file list))
    (message "%s is a invaild directory name" dir-name)))

;;查找指定文件
(defun fs-search-file (file-name point)
  (let ((buf (get-buffer (file-name-nondirectory file-name)))
        (bpt 0))
    (with-current-buffer (find-file-noselect file-name)
      (if buf
          (setq bpt (point)))
      (while point
        (goto-char point)
        (setq point (search-forward fs-file-search-str nil '(nil)))
        (if point
            (let ((b-pt (line-beginning-position))
                  (e-pt (line-end-position)))
              (fs-insert-result
               (count-lines 1 point)
               file-name
               (buffer-substring b-pt e-pt)))))
      (if buf
          (goto-char bpt)
          (kill-buffer (current-buffer))))))

;;给出结果buffer
(defun fs-get-search-result-buffer()
  (get-buffer-create fs-file-search-buffer-name))
 
;;插入查找结果
(defun fs-insert-result (line file text)
  (with-current-buffer (fs-get-search-result-buffer)
      (setq buffer-read-only nil)
      (goto-char (point-max))
      (let ((bpt (point)))
        (insert (file-name-nondirectory file))
        (set-text-properties bpt (point-max) '(face fs-file-name-face))
        (put-text-property bpt (point-max) 'keymap fs-file-search-keymap)
        (put-text-property bpt (point-max) 'filename file)
        (put-text-property bpt (point-max) 'nline line))
      (goto-char (point-max))
      (let ((bpt (point)))
        (insert "(" (number-to-string line)  "): ")
        (set-text-properties bpt (point-max) '(face fs-line-face)))
      (insert text "\n")
      (setq buffer-read-only t)))

;;显示结果窗口
(defun fs-show-result-window ()
  (with-current-buffer (fs-get-search-result-buffer)
    (let ((w (or (get-buffer-window fs-file-search-buffer-name)
                (split-window-vertically -10))))
      (set-window-buffer w (current-buffer))
      (select-window w)
      (goto-line 1))))

;;在查找结果上按回车的处理函数
(defun fs-result-choose()
  (interactive)
  (let ((bpt (line-beginning-position)))
    (let ((line (get-text-property bpt 'nline))
          (file (get-text-property bpt 'filename)))
      (select-window (next-window))
      (find-file file)
      (goto-line line))))

;;查找目录
;;;###autoload
(defun search-directory(str dir match-regexp)
  (interactive "ssearch string: \nDsearch directory: \nsmatch-regexp:")
  (kill-buffer (fs-get-search-result-buffer))
  (setq fs-file-search-str str)
  (setq fs-match-regexp match-regexp)
  (fs-search-directory dir)
  (fs-show-result-window))

;;查找目录
;;;###autoload
(defun search-file(str file)
  (interactive "ssearch string: \nffile:")
  (kill-buffer (fs-get-search-result-buffer))
  (setq fs-file-search-str str)
  (fs-search-file file 1)
  (fs-show-result-window))

(provide 'file-search)

发表于 @ 2007年04月25日 20:52:00|评论(loading...)|编辑

 | 旧一篇: 放弃,才有所得。

评论

#g9yuayon 发表于2007-04-28 11:09:00  IP: 74.123.144.*
这个太有用了。谢谢。
#Soloman 发表于2008-01-24 17:27:28  IP: 203.92.217.*
为什么不用M-x grep
#yeyuboy 发表于2008-02-26 20:01:17  IP: 59.155.252.*
在windows下还真离不了它,谢谢。

有个小问题,当焦点buf中时,按M-x search-file,
最后的查找结果会被放到后台,输出消息如下:
split-window-vertically: Window height 0 too small (after splitting)
发表评论  


当前用户设置只有注册用户才能发表评论。如果你没有登录,请点击登录
Csdn Blog version 3.1a
Copyright © 剑神一笑