# loop2

```(loop for x in '(1 2 3) collect (list x (* x x))) ; => ((1 1) (2 4) (3 9))
(loop for x in '(1 2 3) append (list x (* x x))) ; => (1 1 2 4 3 9)

;; 1から10までの総和を得る
(loop for i from 1 to 10 sum i)		; => 55
;; 1から10までの二乗和を得る
(loop for i from 1 to 10 sum (* i i))	; => 385
;; 二次関数 y = x^2-2x+2の最大値と最小値を求める
(defun y (x) (+ (* x x) (* -2 x) 2))	; => y
;; 0から4までのy(x)の値を求める
(loop for x from 0 to 4 collect (y x))	; => (2 1 2 5 10)
;; 最大値と最小値を求める
(loop for x from 0 to 4 maximize (y x))	; => 10
(loop for x from 0 to 4 minimize (y x))	; => 1

;; countは条件を満たした回数を数える
;; 全要素が奇数のときにt
(loop for x in '(1 3 5) always (oddp x)) ; => t
(loop for x in '(1 2 5) always (oddp x)) ; => nil
;; 全要素が偶数でない (奇数)のときにt
(loop for x in '(1 3 5) never (evenp x)) ; => t
(loop for x in '(1 2 5) never (evenp x)) ; => nil
;; どれかの要素が偶数のときにt
(loop for x in '(1 3 5) thereis (evenp x)) ; => nil
(loop for x in '(1 2 5) thereis (evenp x)) ; => t
;; 奇数の数を数える
(loop for x in '(1 2 5) count (oddp x)) ; => 2

;; 通常のケースはテストの後でdoが実行される
(with-output-to-string
(loop for i from 1 to 2
do (princ i)))			; => "12"
;; テストが後なのでdoが先に実行され、iが後退する
(with-output-to-string
(loop do (princ i)
for i from 1 to 2))		; => "123"
(with-output-to-string
(loop do (princ "X")
for i from 1 to 3
do (princ i)))			; => "X1X2X3X"

;; 複数ループ
(loop for i from 1 to 3
for j from 6 to 8
collect (list i j))		; => ((1 6) (2 7) (3 8))
;; 先に打ち止めになるほうに合わせることもできる
(loop for i from 1 to 3
for j from 6 to 6
collect (list i j))		; => ((1 6))
;; 有限ループの繰り返し節がある場合は無限ループがあってもいい
(loop for i from 1 to 3
for j from 6
collect (list i j))		; => ((1 6) (2 7) (3 8))
;; 並列ループではなくループを入れ子にする場合
(loop for i from 1 to 3 collect
(loop for j from 5 to 6
collect (list i j)))	; => (((1 5) (1 6)) ((2 5) (2 6)) ((3 5) (3 6)))
(loop for i from 1 to 3 append
(loop for j from 5 to 6
collect (list i j)))	; => ((1 5) (1 6) (2 5) (2 6) (3 5) (3 6))
(loop for i from 1 to 3 collect
(loop for j from 5 to 6
append (list i j)))	; => ((1 5 1 6) (2 5 2 6) (3 5 3 6))

;; ローカル変数を作成する
(loop with a = 2
for x from 1 to 3
collect (* x a))			; => (2 4 6)

;; 最後にwithを書いても最初に初期化される
(loop for x from 1 to 3
collect (* x a)
with a = 2)			; => (2 4 6)
;; yは毎回設定される
(loop for x from 1 to 3
for y = (* x 2)
collect (list x y))		; => ((1 2) (2 4) (3 6))

;; ローカル変数を作成する
(let ((a 2)
null)
(loop for x from 1 to 3
collect (* x a)
)
)					; => (2 4 6)

```

P217

Emacs Lispテクニックバイブル