elisp 코드의 성능을 어떻게 측정합니까? 할 수있는 도구 / 외부

elisp 코드의 성능을 어떻게 측정합니까? 소요 시간을 측정 할 수있는 도구 / 외부 패키지는 무엇입니까?

총 시간 외에도 기능별 소요 시간을 보여주는 프로필을 볼 수 있습니까? 메모리 사용량도 프로파일 링 할 수 있습니까?



답변

기준

가장 간단한 옵션은 내장 benchmark패키지입니다. 사용법은 매우 간단합니다.

(benchmark 100 (form (to be evaluated)))

자동로드되므로 필요하지 않아도됩니다.

프로파일 링

벤치 마크는 전체 테스트에 적합하지만 성능 문제가있는 경우 어떤 기능이 문제를 일으키는 지 알려주지 않습니다. 이를 위해 (내장) 프로파일 러가 있습니다.

  1. 로 시작하십시오 M-x profiler-start.
  2. 시간이 많이 걸리는 작업을 수행하십시오.
  3. 로 보고서를 받으십시오 M-x profiler-report.

탐색 가능한 함수 호출 트리가있는 버퍼로 이동해야합니다.
프로파일 러 스크린 샷


답변

@Malabara의 답변 외에도 사용자 정의 with-timer매크로를 사용하여 코드의 다양한 부분 (예 : init.el파일) 을 영구적으로 계측 하는 경향이 있습니다 .

차이점은 benchmark계측하는 특정 코드 비트의 성능을 연구 할 수 있지만 with-timer항상 코드의 각 계측 된 부분에 소요되는 시간 (충분히 큰 부분에 대한 오버 헤드없이)을 제공한다는 점입니다. 어떤 부분을 더 조사해야하는지

(defmacro with-timer (title &rest forms)
  "Run the given FORMS, counting the elapsed time.
A message including the given TITLE and the corresponding elapsed
time is displayed."
  (declare (indent 1))
  (let ((nowvar (make-symbol "now"))
        (body   `(progn ,@forms)))
    `(let ((,nowvar (current-time)))
       (message "%s..." ,title)
       (prog1 ,body
         (let ((elapsed
                (float-time (time-subtract (current-time) ,nowvar))))
           (message "%s... done (%.3fs)" ,title elapsed))))))

사용 예 :

(with-timer "Doing things"
  (form (to (be evaluated))))

*Messages*버퍼에 다음과 같은 출력이 나타납니다 .

Doing things... done (0.047s)

Jon Wiegley의 use-package-with-elapsed-timer뛰어난 use-package확장 기능 에서 큰 영향을 받았다는 점을 언급해야 합니다.


답변

@Malabarba의 답변 외에도을 사용 하여 코드 의 컴파일 된 실행 시간을 측정 할 수 있습니다 benchmark-run-compiled. 이 메트릭은 종종 다음 을 제공 하는 해석 된 실행 시간 보다 훨씬 관련성이 M-x benchmark있습니다.

ELISP> (benchmark-run (cl-loop for i below (* 1000 1000) sum i))
(0.79330082 6 0.2081620540000002)

ELISP> (benchmark-run-compiled (cl-loop for i below (* 1000 1000) sum i))
(0.047896284 0 0.0)

세 개의 숫자는 총 경과 시간, GC 실행 횟수 및 GC에 소요 된 시간입니다.


답변

벤치마킹은 숫자를 얻는 것뿐만 아니라 결과 분석을 기반으로 결정을 내리는 것입니다.

MELPA 에는 benchstat.el 패키지 가 있으며 benchstat 프로그램이 제공 하는 기능을 얻는 데 사용할 수 있습니다 .

비교 X속성 벤치마킹을 구현하여 에 대한 성능 속성 을 검사 합니다 Y.

Benchstat 함수는 benchmark-run-compiled정보를 수집 할뿐만 아니라 해석 형식을 쉽게 읽을 수 있는 래퍼 로 볼 수 있습니다 . 다음을 포함합니다 :

  • X와 사이의 경과 시간 델타Y
  • 평균 평균 시간
  • 할당 금액

매우 간단한 사용법 예 :

(require 'benchstat)

;; Decide how much repetitions is needed.
;; This is the same as `benchmark-run-compiled` REPETITIONS argument.
(defconst repetitions 1000000)

;; Collect old code profile.
(benchstat-run :old repetitions (list 1 2))
;; Collect new code profile.
(benchstat-run :new repetitions (cons 1 2))

;; Display the results.
;; Can be run interactively by `M-x benchstat-compare'.
(benchstat-compare)

benchstat-compare임시 버퍼에 결과를 렌더링 :

name   old time/op    new time/op    delta
Emacs    44.2ms ± 6%    25.0ms ±15%  -43.38%  (p=0.000 n=10+10)

name   old allocs/op  new allocs/op  delta
Emacs      23.0 ± 0%      11.4 ± 5%  -50.43%  (p=0.000 n=10+10)

benchstat그래도 프로그램 바이너리 가 필요 합니다. Go 프로그래밍 언어를 사용한 경우 시스템에 이미 언어가있는 것 같습니다. 그렇지 않으면 소스에서 컴파일하는 옵션이 있습니다.

linux / amd64 용 사전 컴파일 된 바이너리는 github release page 에서 찾을 수 있습니다 .


답변