C言語の関連ファイルを開く


C言語でプログラミングする際、今開いているファイルに関連するファイルを開きたいことが結構ある。
例えば、hoge.cを開いている際にhoge.hを開きたい、という風に。
Emacsでは(自分の場合)以下の手順で関連ファイルを開く。

手順その1

  1. M-x find-file(C-x C-f)
  2. ミニバッファでhoge.hを入力

もしくは、

手順その2

  1. elscreen-create(自分の場合は、C-o c)
  2. M-x find-file(C-x C-f)
  3. ミニバッファでhoge.hを入力

あるいは、

手順その3

  1. ウインドウを左右に分割(split-window-horizontally)
  2. C-x oで移動
  3. M-x find-file(C-x C-f)
  4. ミニバッファでhoge.hとを入力


今のところ、手順その1で開くことはほとんどない。
ただ、ほかの手順はステップ数が微妙に多いので、自動化することにした。
なんか既にありそうな気もしたが、見つからなかったので、自分で書いた。*1

(defun c-open-relational-file (how-open-type)
  (interactive "nOpen-Type: ")
  (defun get-opened-file-name-prefix (file-name)
    (string-match "^\\([^.]+\\)\\.[^.]+$" file-name)
    (match-string 1 file-name))
  (defun get-ext-type (file-name)
    (string-match "\\.\\([^.]+\\)$" file-name)
    (match-string 1 file-name))
  (let* ((ext-map '(
                    ("h" . "c")
                    ("c" . "h")
                    ))
         (opened-file-name (buffer-file-name (window-buffer)))
         (opened-file-name-prefix (get-opened-file-name-prefix opened-file-name))
         (opened-file-ext-type (get-ext-type opened-file-name))
         (opening-file-ext-type (cdr (assoc opened-file-ext-type ext-map)))
         (opening-file-name (concat opened-file-name-prefix "." opening-file-ext-type))
         (opening-file-buffer (find-file-noselect opening-file-name)))
    (cond ((= how-open-type 1) (elscreen-switch-or-create opening-file-buffer))
          ((= how-open-type 2) (progn (split-window-horizontally)
                                      (other-window 1)
                                      (switch-to-buffer opening-file-buffer)))
          (t                   (message "Illegal Type")))))


改良点としては、一つの拡張子に対して複数の拡張子を関連づけられるようにすることかな。
アセンブラのファイル(.s)を開くかもしれないし、あと、C++だとなんか拡張子がいっぱいあるし。
cpp、c++、h++、hpp、cxx、・・・なんかまだあったような気がする。

*1:elscreen-switch-or-createは前に書いた[http://d.hatena.ne.jp/cubicdaiya/20080104/1199435498:title=これ]