使用Emacs作为IDE

时间:2008-09-15 14:31:23

标签: emacs ide development-environment slime

目前,当我使用C或C ++编码时,我使用Emacs的工作流涉及三个窗口。右边最大的包含我正在使用的文件。左边分为两个,底部是我用来输入编译或make命令的shell,top通常是我在工作时想要咨询的某种文档或README文件。现在我知道有一些非常专业的Emacs用户,我很好奇其他Emacs在功能上是有用的,如果打算将它用作一个完整的IDE。具体来说,大多数IDE通常以某种形式实现这些功能:

  • 源代码编辑器
  • 编译器
  • 调试
  • 文档查找
  • 版本控制
  • 类查找和对象检查器等OO功能

对于其中的一些,很明显Emacs如何适应这些功能,但其余的呢?此外,如果必须关注特定语言,我会说它应该是C ++。

编辑:有一位用户指出,当我说'剩下的'时,我应该更具体一些。大多数情况下,我对有效的版本控制以及文档查找感到好奇。例如,在SLIME中,在Lisp函数上进行快速hyperspec查找相当容易。有没有快速查找C ++ STL文档中的内容(例如,如果我忘记了hash_map的确切语法)?

18 个答案:

答案 0 :(得分:73)

你必须具体说明“其余”是什么意思。除了对象检查器(我知道)之外,emacs很容易完成上述所有操作:

  • 编辑(显而易见)
  • 编译器 - 只需运行M-x compile并输入编译命令。从那以后,您可以M-x compile使用默认值。 Emacs将捕获C / C ++编译器错误(最适合GCC)并帮助您导航到有警告或错误的行。
  • 调试 - 类似地,当您要调试时,键入M-x gdb并创建一个带有特殊绑定的gdb缓冲区
  • 文档查找 - emacs具有出色的CScope绑定代码导航功能。对于其他文档:Emacs还有一个手册页阅读器,其他一切都有网页和书籍。
  • 版本控制 - 对于各种VCS后端有许多Emacs绑定(CVS,SCCS,RCS,SVN,GIT都会浮现在脑海中)

编辑:我意识到我关于文档查找的答案确实与代码导航有关。这里有一些更为重要的信息:

谷歌搜索无疑会揭示更多的例子。

正如第二个链接所示,即使不支持开箱即用,也可以在其他文档中查找功能(以及其他任何内容)。

答案 1 :(得分:29)

我必须推荐Emacs Code Browser作为emacs的更“传统”的IDE风格环境。

编辑:我现在还推荐Magit高度优于emacs中的标准VCS界面。

答案 2 :(得分:19)

您是否尝试过M-x编译,而不是在shell窗口中运行make命令?它将运行make命令,显示错误,并且在许多情况下,如果输出包含文件名和行号,则很容易跳转到导致错误的代码行。

如果您是IDE的粉丝,您可能还想查看emacs的speedbar包(M-x speedbar)。而且,如果您还没有,请了解如何使用标签表来导航代码。

答案 3 :(得分:15)

曾经发现过的emacs角落会让您以前所未有的方式提高工作效率。正如其他人所提到的,使用标签是缩放源代码的一种极好而快速的方法,使用M- /(dabbrev-expand)通常可以完成您在完成变量名称时的预期。

使用occurrence对于获取缓冲区中包含正则表达式的所有出现的缓冲区非常有用。这在重构代码和查找代码片段或使用变量时非常方便,或者如果您在源文件中使用TODO标记并且想要全部访问它们。

flush-lines,sort-numeric-fields,replace-regexp和rectangle函数对于从某个工具获取转储并将其转换为有用的数据(如elisp程序或逗号分隔的电子表格)非常有用。

我写了一个关于IDE的页面,就像你可以用emacs做的那样

http://justinsboringpage.blogspot.com/2007/09/11-visual-studio-tricks-in-emacs.html

学习elisp是另一种很好的方式来回答你自己除了典型的IDE之外还能做些什么。

例如,我发表了关于编写Perforce辅助函数(如blame)的博客(编写自己的函数意味着可以使其行为完全符合您的要求)...

http://justinsboringpage.blogspot.com/2009/01/who-changed-line-your-working-on-last.html

我还编写了动态创建函数注释的代码,它与我正在使用的编码标准相匹配。

我的elisp代码都不是特别棒,而且大多数代码已经存在于库中,但是能够让emacs做一些工作日中出现的自定义内容非常有用。

答案 4 :(得分:10)

你可以找到emacs&的详细说明。 my site上的版本控制集成。我也在撰写关于将Emacs用作许多语言的开发环境的文章 - C / C ++,Java,Perl,Lisp / Scheme,Erlang等......

答案 5 :(得分:8)

对于版本控制,您可以使用多种内容,具体取决于您使用的版本控制系统。但是其中一些功能对所有功能都很常见。

vc.el 是在文件级别处理版本控制的内置方法。它具有大多数版本控制系统的后端。例如,Subversion后端附带了Emacs,还有其他来源的git后端和其他。

最有用的命令是 C-x v v (vc-next-action),它为您正在访问的文件执行适当的下一步操作。这可能意味着从存储库更新或提交更改,如果您使用的是需要它的系统(如RCS),vc.el还会重新绑定 C-x C-q 以签入和签出文件。

其他非常有用的命令是 C-x v l C-x v = ,它们显示您正在使用的文件的日志和当前差异。

但是为了实现真正的工作效率,除了简单的事情外,你应该避免使用单文件vc.el命令。有几个软件包可以为您提供整个树状态的概述,并为您提供更多功能,更不用说能够创建跨越多个文件的连贯提交。

其中大部分受到严重影响或基于CVS的原始 pcl-cvs / pcvs 。甚至还有两个与subversion一起出现, psvn.el dsvn.el 。有git等包。

答案 6 :(得分:8)

好的,这里的每个人都在提供完美的提示,使emacs成为一个出色的IDE。

但是任何人都应该记住,当你定制你的emacs有很多扩展(特别是那些用于动态类型检查,功能定义查找等)你的emacs将加载非常非常慢的编辑器。

要解决此问题,我强烈建议您在server mode中使用emacs。

使用起来非常简单,无需自定义init文件。 您只需要以守护进程模式启动emacs;

emacs --daemon

这将创建一个emacs服务器,然后您可以从终端或gui连接它。我还建议创建一些别名,以便于调用。

alias ec="emacsclient -t"
alias ecc="emacsclient -c &"
# some people also prefer this but no need to fight here;
alias vi="emacsclient -t"

这样,emacs的启动速度甚至比gedit还要快。承诺。

这里可能出现的一个问题是,如果您从临时用户运行emacs守护程序,则可能无法将emacs服务器连接为root

因此,如果您需要打开具有root访问权限的文件;请改用tramp。只需使用普通用户运行emacs客户端并打开这样的文件;

C-x C-f
/sudo:root@localhost/some/file/that/has/root/access/permissions
# on some linux distro it might be `/su:root@...` 

这让我的生活变得更轻松,我可以用这种方式在几毫秒内打开我沉重的自定义python IDE。您可能还想将emacs --daemon添加到系统启动,或者为emacsclient创建桌面文件。随你(由你决定。

有关emacs守护程序和emacs客户端的更多信息,请访问wiki;

http://www.emacswiki.org/emacs/EmacsAsDaemon

http://www.emacswiki.org/emacs/EmacsClient

答案 7 :(得分:7)

我同意你应该学习M-x编译(将那个和M-x下一个错误绑定到一个短键序列)。

了解版本控制的绑定(例如vc-diff,vc-next-action等)

查看寄存器。您不仅可以记住缓冲区中的位置,还可以记住整个窗口配置(C-x r w - 窗口配置到寄存器)。

答案 8 :(得分:6)

用于探索Emacs的VC功能的起点(可能不明显)是 M-x vc-next-action

它在当前文件上执行“下一个逻辑版本控制操作”,具体取决于文件的状态和VC后端。因此,如果文件不受版本控制,则会对其进行注册,如果文件已更改,则会提交更改等。

需要一点时间习惯,但我发现它非常有用。

默认键绑定是 C-x v v

答案 9 :(得分:4)

有一个TFS.el for emacs integration into Microsoft TFS。它适用于任何TFS,包括运行Codeplex.com的TFS。

设置的基本步骤:

  1. 将tfs.el放在您的加载路径中。

  2. 在您的.emacs文件中:

    (require 'tfs)
    (setq tfs/tf-exe  "c:\\vs2008\\common7\\ide\\tf.exe")
    (setq tfs/login "/login:domain\\userid,password")
          -or-
    (setq tfs/login (getenv "TFSLOGIN"))  ;; if you have this set
    
  3. 也在.emacs文件中,为tfs命令设置本地或全局键绑定。像这样:

    (global-set-key  "\C-xvo" 'tfs/checkout)
    (global-set-key  "\C-xvi" 'tfs/checkin)
    (global-set-key  "\C-xvp" 'tfs/properties)
    (global-set-key  "\C-xvr" 'tfs/rename)
    (global-set-key  "\C-xvg" 'tfs/get)
    (global-set-key  "\C-xvh" 'tfs/history)
    (global-set-key  "\C-xvu" 'tfs/undo)
    (global-set-key  "\C-xvd" 'tfs/diff)
    (global-set-key  "\C-xv-" 'tfs/delete)
    (global-set-key  "\C-xv+" 'tfs/add)
    (global-set-key  "\C-xvs" 'tfs/status)
    (global-set-key  "\C-xva" 'tfs/annotate)
    (global-set-key  "\C-xvw" 'tfs/workitem)
    

答案 10 :(得分:3)

compile,next-error和previous-error都是Emacs中C ++开发非常重要的命令(在grep输出上也很好用)。 Etags,visit-tags-table和find-tag也很重要。 completion.el是20世纪最伟大的黑客攻击之一,可以将你的C ++黑客加速一个数量级。哦,我们不要忘记ediff。

我还没有学习如何在不访问shell的情况下使用版本控制,但现在我正在更频繁地运行提交(使用git),我可能不得不这样做。

答案 11 :(得分:3)

您可能还会发现tabbar有用。它模拟了从Eclipse迁移到Emacs时我唯一遗漏的行为。绑定到“,”和“。”要移动到上一个和下一个标签栏,它会让您无法一直按Ctrl-x b切换缓冲区。

不幸的是,提到的网页没有提供正确的下载版本。但是,大多数Ubuntu版本都在他们的emacs-goodies包中提供它。

答案 12 :(得分:3)

我在Windows上使用emacs。编译模块很好,但我希望编译更聪明地建议编译命令行。 It's possible to use "File Variables" to specify compile-command,但我想要比这更聪明的东西。所以我写了一个小功能来帮忙。它在运行compile时猜测要使用的编译命令,以提示用户。

guess函数查找vbproj或csproj或sln文件,如果找到,则建议使用msbuild。然后它查看缓冲区文件名,并根据它,建议不同的东西。 .wxs文件意味着它是一个WIX项目,您可能想要构建一个MSI,因此猜测逻辑建议MSI的nmake命令。如果它是一个Javascript模块,那么建议是运行jslint-for-wsh.js来lint .js文件。作为后备,它表明了nmake。

我使用的代码如下所示:

(defun cheeso-guess-compile-command ()
  "set `compile-command' intelligently depending on the
current buffer, or the contents of the current directory."
  (interactive)
  (set (make-local-variable 'compile-command)
       (cond
        ((or (file-expand-wildcards "*.csproj" t)
             (file-expand-wildcards "*.vcproj" t)
             (file-expand-wildcards "*.vbproj" t)
             (file-expand-wildcards "*.shfbproj" t)
             (file-expand-wildcards "*.sln" t))
         "msbuild ")

        ;; sometimes, not sure why, the buffer-file-name is
        ;; not set.  Can use it only if set.
        (buffer-file-name
         (let ((filename (file-name-nondirectory buffer-file-name)))
           (cond

            ;; editing a .wxs (WIX Soluition) file
            ((string-equal (substring buffer-file-name -4) ".wxs")
             (concat "nmake "
                     ;; (substring buffer-file-name 0 -4) ;; includes full path
                     (file-name-sans-extension filename)
                     ".msi" ))

            ;; a javascript file - run jslint
            ((string-equal (substring buffer-file-name -3) ".js")
             (concat (getenv "windir")
                     "\\system32\\cscript.exe c:\\users\\cheeso\\bin\\jslint-for-wsh.js "
                     filename))

            ;; something else - do a typical .exe build
            (t
             (concat "nmake "
                     (file-name-sans-extension filename)
                     ".exe")))))
        (t
         "nmake "))))


(defun cheeso-invoke-compile-interactively ()
  "fn to wrap the `compile' function.  This simply
checks to see if `compile-command' has been previously set, and
if not, invokes `cheeso-guess-compile-command' to set the value.
Then it invokes the `compile' function, interactively."
  (interactive)
  (cond
   ((not (boundp 'cheeso-local-compile-command-has-been-set))
    (cheeso-guess-compile-command)
    (set (make-local-variable 'cheeso-local-compile-command-has-been-set) t)))
  ;; local compile command has now been set
  (call-interactively 'compile))

;; in lieu of binding to `compile', bind to my monkeypatched function
(global-set-key "\C-x\C-e"  'cheeso-invoke-compile-interactively)

我尝试将此作为编译功能的“建议之前”,但无法令人满意地工作。所以我定义了一个新函数,并将它绑定到我用于compile的同一个击键组合。


  

编辑现在有了“smarter-compile.el”,这让这个想法更进了一步。

答案 13 :(得分:2)

文档查找:这取决于您的编程语言。

C库和系统调用通常记录在手册页中。为此,您可以使用M-x man。在信息页面中可以更好地记录一些内容;使用M-x info

对于elisp本身,请使用C-h f。对于python,请在解释器中使用>>> help(<function, class, module>)

我发现大多数其他语言都提供html格式的文档。为此,尝试嵌入式浏览器(我使用w3m)。将BROWSER环境变量设置为围绕emacsclient -e "(w3m-goto-url-new-session \"$@\")"(on * nix)的包装脚本,以防某些内容可能会打开浏览器并且您希望它在emacs中打开。

答案 14 :(得分:2)

我知道这是一个很老的帖子。但是这个问题对emacs初学者是有效的。

IMO使用emacs的最佳方法是将language server protocol与emacs一起使用。您可以在链接的网站中找到有关语言服务器的所有信息。

为快速进行设置,我敦促您转到此页面eglot。 IMO eglot做得很好。它与公司等自动完成程序包很好地集成在一起。提供查找参考,以及更多。

对于调试器而言,您可能还需要针对特定​​语言的特定调试器。您可以在emacs中使用gdb。只需输入M-x gdb即可。

要编译代码,最好使用shell命令。我正在从事这个项目eproj。需要一段时间才能完成。但是它所做的只是将shell命令映射到项目类型。并通过外壳构建项目。执行命令的方法相同。我可能需要帮助来完成这个项目。它尚未准备好使用,但是如果您了解一些elisp,则可以遍历代码。

此外,始终最好使用emacs编译命令。

对于版本控制,我还没有看到任何其他可以与magit媲美的软件包。它特定于git。另外对于git还有另一个软件包git-timemachine,我觉得它非常有用。

对象查找和类查找由语言服务器协议提供。

项目树可用于与treemacs的ide界面。

还有一个名为projectile的项目交互库。

对于自动完成功能,我发现company-mode非常有用。

真正的emacs可以做任何事情。

答案 15 :(得分:1)

近年来,Clang成为Emacs C ++支持的重要组成部分。 Atila Neves在2015年CppCon上发表了演讲: "Emacs as a C++ IDE"

这是一个16分钟的演讲,他在那里展示了以下主题的解决方案:

  • 跳转到定义
  • 自动完成
  • 动态语法突出显示
  • 在项目中查找文件

可以找到幻灯片here

答案 16 :(得分:0)

在Unix或X windows风格中,我不知道有一个适用于所有内容的集成IDE。

要与调试器交互,只需IDE的一个组件,请考虑realgud。我觉得有用的另一件事是用于位置消息的解析器,因此如果你有一个调用堆栈跟踪并且想要在callstack中的特定位置进行编辑,那么这个前端接口就可以做到这一点。

到目前为止,该计划可以使用改进。但是,它也可以使用人们来改进它。

免责声明:我致力于realgud

答案 17 :(得分:0)

尝试lsp模式。现在,您可以在连接到服务器的emacs中使用其他IDE功能。寻找更多信息:lsp-mode