33 lines
975 B
Common Lisp
33 lines
975 B
Common Lisp
(defun dot (a b)
|
|
"Returns the dot product of vectors A and B"
|
|
(reduce #'+ (mapcar #'* a b)))
|
|
|
|
(defun right-triangle-p (o p q)
|
|
"Returns non-NIL if the triangle made by points O, P, and Q (integer coordinates) is a right triangle"
|
|
(loop with op = (mapcar #'- o p)
|
|
with pq = (mapcar #'- p q)
|
|
with qo = (mapcar #'- q o)
|
|
repeat 3
|
|
do (when (= 0 (dot op pq))
|
|
(return t))
|
|
(rotatef op pq qo)))
|
|
|
|
(defun right-triangles-with-integer-coordinates (&optional (max 50))
|
|
(let ((count 0)
|
|
(mirrored (make-hash-table :test 'equal))
|
|
(o (list 0 0)))
|
|
(loop for x1 from 0 upto max do
|
|
(loop for y1 from 0 upto max do
|
|
(loop for x2 from 0 upto max do
|
|
(loop for y2 from 0 upto max do
|
|
(let ((p (list x1 y1))
|
|
(q (list x2 y2)))
|
|
(when (and (not (equal p q))
|
|
(not (equal o p))
|
|
(not (equal o q))
|
|
(not (gethash (append p q) mirrored))
|
|
(right-triangle-p o p q))
|
|
(setf (gethash (append q p) mirrored) t)
|
|
(incf count)))))))
|
|
count))
|