I'm trying to convert this Python code into Common Lisp:
for a in xrange(1,1000):
for b in xrange(a,1000):
c = (a**2 + b**2) ** 0.5
s = a + b + c
if s == 1000:
return a * b * c
My first attempt was:
(loop for a from 1 to 999
do (loop for b from a to 999
for c = (sqrt (+ (expt a 2) (expt b 2)))
for s = (+ a b c)
until (= s 1000)
finally return (* a b c))))
This doesn't work. My task is: when s
hits 1000 make the whole expression above return (* a b c)
. How to return some value from a nested loop macro?
You can use block
and return-from
operators: block
establishes a named block of code, and you can return from this block with return-from
using the name of the block
(let (c s)
(block nested-loops
(do ((a 1 (1+ a))) ((= a 999))
(do ((b a (1+ b))) ((= b 999))
(setf c (sqrt (+ (expt a 2) (expt b 2)))
s (+ a b c))
(if (= s 1000)
(return-from nested-loops (* a b c)))))))
PS, I don't use loop
here, I just got used to do
.
Also from http://www.gigamonkeys.com/book/loop-for-black-belts.html
To allow RETURN-FROM to be used to return from a specific loop (useful when nesting LOOP expressions), you can name a LOOP with the loop keyword named. If a named clause appears in a loop, it must be the first clause. For a simple example, assume lists is a list of lists and you want to find an item that matches some criteria in one of those nested lists. You could find it with a pair of nested loops like this:
(loop named outer for list in lists do
(loop for item in list do
(if (what-i-am-looking-for-p item)
(return-from outer item))))
The Python return
statement doesn't return from the loop, it returns from the whole function that the loop is contained in. In Common Lisp, a function establishes an implicit block with the same name as the function. So you can use:
(return-from function-name (* a b c))
to perform the return equivalent to the Python code.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With