문자열에 포함 된 Elisp 코드를 평가하는 방법은 무엇입니까?


21

질문은 거의 모든 것을 말합니다 : 유효한 Elisp 표현식의 소스 코드가 포함 된 문자열이 있고 평가하고 싶습니다.

예를 들어 Python에서는 표현식 eval("1 - 2 + 3")이 2로 평가됩니다.


2
참고 (calc-eval "1 - 2 + 3")이 유효 elisp없는 경우에도 더 나은 파이썬 예를 들어 맞는다. 아직 calc패키지 가 필요하지 않은 경우 패키지를로드하기 전에를로드해야합니다 (require 'calc). (나는 이것이 당신의 질문에 대답하지 않는다는 것을 알고 있습니다. 따라서 그것은 의견으로 공식화됩니다.)
Tobias

답변:


24

elisp 코드 문자열을 평가하는 것은 2 단계 프로세스입니다.를 사용하여 문자열을 구문 분석 read-from-string한 다음 결과 Lisp 표현식을로 평가해야합니다 eval.

(defun my-eval-string (string)
  "Evaluate elisp code stored in a string."
  (eval (car (read-from-string string))))

이제로 (my-eval-string "(+ 1 2)")평가됩니다 3.

편집하다:

에 의해 지적 @lunaryorn , read-from-string 첫 번째 식을 읽고 이 더 있어야한다, 그래서 :

(defun my-eval-string (string)
  (eval (car (read-from-string (format "(progn %s)" string)))))

편집 2 :

부작용에 대한 elisp 코드를 평가하기 위해 with-temp-bufferand 를 사용할 수도 있습니다 eval-buffer( eval-buffer항상 nil).

(defun my-eval-string-for-side-effects (string)
  "Evaluate a string of elisp code for side effects."
  (with-temp-buffer
    (insert string)
    (eval-buffer)))

(my-eval-string-for-side-effects "(message \"hello!\")")

with-temp-buffer덜 이상적입니다 때문에 모든 버퍼 관련 호출 예와 엉망 buffer-file-name...
하 - 두옹 구엔

5

콘스탄틴의 대답은 괜찮습니다.

약간의 수정 만 제공하면됩니다.

(defun my-eval-string (str)
  "Read and evaluate all forms in str.
Return the results of all forms as a list."
  (let ((next 0)
        ret)
    (condition-case err
        (while t
          (setq ret (cons (funcall (lambda (ret)
                                     (setq next (cdr ret))
                                     (eval (car ret)))
                                   (read-from-string str next))
                          ret)))
      (end-of-file))
    (nreverse ret)))

(my-eval-string "1 2 3 (+ 3 1)")

마지막 양식은 목록을 반환합니다 (1 2 3 4).

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.