From: Ari Krupnik
Subject: loop with an optional limit?
Date: 
Message-ID: <86y7uu10r8.fsf@deb.lib.aero>
I'm trying to write a function that reads forms from a file. The
caller may optionally specify a maximum number of forms to read; if
that variable is null, the function should read forms until eof. Is
there a way to do this with loop? The best I've been able to come up
with is really ugly:

(loop for n = 0 then (1+ n)
      for form = (read s nil 'eof)
      until (or (eql form 'eof)
                (when max-forms         ; max-forms is &optional
                      (>= n max-quotes)))
      collecting (make-instance 'foo :src form))


This looks cleaner, but of course only works if max-quotes is a
number.

(loop repeat max-quotes
      for form = (read s nil 'eof)
      until (eql form 'eof)
      collecting (make-instance 'foo :src form))

Ari.

-- 
Elections only count as free and trials as fair if you can lose money
betting on the outcome.

From: Pascal Bourguignon
Subject: Re: loop with an optional limit?
Date: 
Message-ID: <87lkquuh49.fsf@thalassa.informatimago.com>
Ari Krupnik <···@lib.aero> writes:

> I'm trying to write a function that reads forms from a file. The
> caller may optionally specify a maximum number of forms to read; if
> that variable is null, the function should read forms until eof. Is
> there a way to do this with loop? The best I've been able to come up
> with is really ugly:
>
> (loop for n = 0 then (1+ n)
You can let loop do the increment for you.
>       for form = (read s nil 'eof)
eof could be present in the file.
>       until (or (eql form 'eof)
>                 (when max-forms         ; max-forms is &optional
>                       (>= n max-quotes)))
>       collecting (make-instance 'foo :src form))

(loop 
  :for n :from 1
  :for form = (read s nil s)
  :until (eq form s)
  :collect (make-instance 'foo :src form)
  :until (and count (<= count n)))


  
-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

In a World without Walls and Fences, 
who needs Windows and Gates?
From: Ari Krupnik
Subject: Re: loop with an optional limit?
Date: 
Message-ID: <86psg60xrb.fsf@deb.lib.aero>
Pascal Bourguignon <···@informatimago.com> writes:

> Ari Krupnik <···@lib.aero> writes:
>
>> (loop for n = 0 then (1+ n)
> You can let loop do the increment for you.

I was not aware that to or downto was optional.

>>       for form = (read s nil 'eof)
> eof could be present in the file.

Not in this file, but your idiom is clearly superior. Thank you. Also
I see that eq is more appropriate here. I'm still learning to pick the
right equality functions.

>>       until (or (eql form 'eof)
>>                 (when max-forms         ; max-forms is &optional
>>                       (>= n max-quotes)))
>>       collecting (make-instance 'foo :src form))
>
> (loop 
>   :for n :from 1
>   :for form = (read s nil s)
>   :until (eq form s)
>   :collect (make-instance 'foo :src form)
>   :until (and count (<= count n)))

-- 
Elections only count as free and trials as fair if you can lose money
betting on the outcome.
From: Novus
Subject: Re: loop with an optional limit?
Date: 
Message-ID: <2006071922432116807-novus@ngoqdeorg>
On 2006-07-16 03:46:30 -0400, Pascal Bourguignon <···@informatimago.com> said:

> (loop   :for n :from 1
>   :for form = (read s nil s)
>   :until (eq form s)
>   :collect (make-instance 'foo :src form)
>   :until (and count (<= count n)))

Or if you like loops that look more like lisp than loop:

(iter (for form in-stream s)
      (for n upfrom 0)
      (until (and count (<= count n)))
      (collect (make-instance 'foo :src form))))

Novus