現在のファイルでパッケージ宣言を検索するには、次のコードを試してください。
(save-excursion
(goto-char (point-min))
(when (re-search-forward "^\\s *package\\s +\\(.*\\);" (point-max) t)
(match-string 1)))
package
これは、宣言とセミコロンの間の値を返します。nil
そのような宣言が見つからない場合は返されます。
package
( C スタイルの複数行コメント ( ) で、実際のパッケージ宣言の前にコメントアウトされた宣言がある場合、これは失敗する可能性があることに注意してください/* ... */
)。
シェル コマンドを実行するディレクトリを変更するには、cd
関数を使用します。Java では、パッケージ構造はディレクトリ構造を反映する必要があるため、上記のコードによって決定されたパッケージ情報を使用して、ソース コードのベース ディレクトリを特定できます。
(let ((directory (file-name-directory (buffer-file-name)))
(sub-dirs (reverse (split-string package "\\."))))
(while sub-dirs
(if (string-match (concat "^\\(.*/\\)" (regexp-quote (car sub-dirs)) "/$") directory)
(setq directory (match-string 1 directory)
sub-dirs (cdr sub-dirs))
(error "Package does not match directory structure")))
(cd directory))
このコードを使用して、関数を次のように拡張できます。
(defun java-run-current-file ()
"Runs the java program the current file corresponds to"
(interactive)
(let* ((package (save-excursion
(goto-char (point-min))
(when (re-search-forward "^\\s *package\\s +\\(.*\\);" (point-max) t)
(match-string 1))))
(directory (file-name-directory (buffer-file-name)))
sub-dirs)
(if directory
(setq directory (file-truename directory))
(error "Current buffer is not visiting a file"))
(when package
(setq sub-dirs (reverse (split-string package "\\.")))
(while sub-dirs
(if (string-match (concat "^\\(.*/\\)" (regexp-quote (car sub-dirs)) "/$") directory)
(setq directory (match-string 1 directory)
sub-dirs (cdr sub-dirs))
(error "Package does not match directory structure"))))
(cd directory)
(shell-command
(concat "java "
(if package (concat package ".") "")
(file-name-sans-extension
(file-name-nondirectory (buffer-file-name)))))))