Skip to content

crazy loop error.

16 messages · Roy Mathew, Erik Iverson, Petr Savicky +4 more

#
Roy,

I have no idea what you're actually trying to do here, but
it looks like there would be a more natural R'ish way if
you're concerned about grouping consecutive elements of 'a'.

At any rate, within your while loop, you're incrementing n by
1, and eventually n will be 10, which will be transformed to
11 when you add 1 to it, and a[11] will be NA, thus the error
you receive...
Roy Mathew wrote:
#
On Mon, Jan 24, 2011 at 07:16:58PM +0100, Roy Mathew wrote:
Hi.

The for-loop "for (i in 1:k)" uses an internal index, which counts
the repetitions. This is necessary, since the control over a loop
like "for (i in c(1,1,1,1))" cannot be based on the variable i only.
Hence, changing i does not influence the next iteration of the loop.
For example, the following loop always makes m*n repetitions, although
using the same variable in nested loops is definitely not suggested.

  m <- 3
  n <- 5
  for (i in seq(length=m)) {
      for (i in seq(length=n)) {
          cat("*")
      }
      cat("\n")
  }

Hope this helps.

Petr Savicky.
#
Roy Mathew wrote:
Is this the idea you're trying to execute?  It uses ?rle and ?mapply.

a <- c(2,3,5,5,5,6,6,7)
mapply(rep, "hello", rle(a)$lengths, USE.NAMES = FALSE)

[[1]]
[1] "hello"

[[2]]
[1] "hello"

[[3]]
[1] "hello" "hello" "hello"

[[4]]
[1] "hello" "hello"

[[5]]
[1] "hello"
#
On Mon, Jan 24, 2011 at 11:18:35PM +0100, Roy Mathew wrote:
Hi.

A for-loop in R is different from a for-loop in C. It is similar
to foreach loop in Perl. If v is a vector, then

  for (n in v)

first creates the vector v and then always performs length(v) iterations.
Before iteration i, n is assigned v[i] even if n is changed in the
previous iteration.

If you want to control the loop variable during execution, it is possible
to use a while loop, where you have full control. While loop may be better
also if v has a very large length, since, for example

  for (n in 1:1000000)

creates a vector of length 1000000 in memory.

It should also be noted that the for-loop

  for (n in 1:k)

performs 2 iterations, if k is 0, since 1:0 is a vector of length 2.
If k may be 0, then it is better to use

  for (n in seq(length=k))

since seq(length=0) has length 0.

Hope this helps.

Petr Savicky.
#
Hi


r-help-bounces at r-project.org napsal dne 24.01.2011 23:18:35:
elements
the
but
grouped '3
the
Put it into a foo function and make use debug(fun())

Regards
Petr

BTW mapply solution is shorter and probably quicker and easier to 
maintain.
http://www.R-project.org/posting-guide.html
#
On Tue, Jan 25, 2011 at 09:05:03AM +0100, Petr Savicky wrote:
[...]
I forgot that ?break? may stop the loop. See ?"for" for further
information. In particular, it says

  You can assign to ?var? within the body of the loop, but
  this will not affect the next iteration.

Petr Savicky.
#
On Tue, 25 Jan 2011, Petr Savicky wrote:

            
And also if v is changed during the loop.
Since you keep mentioning that, it is actually much better to use 
seq_len(k) (and seq_along(x) instead of your earlier recommendation of 
seq(along=x)).  And if you are using seq() in other cases in programs, 
consider seq.int() instead.

  
    
#
Mr Ripley,

May I ask why seq_len() and seq_along() are better than seq()?

Thanks,
Ivan

Le 1/25/2011 09:58, Prof Brian Ripley a ?crit :

  
    
#
Hi

r-help-bounces at r-project.org napsal dne 25.01.2011 10:58:36:
it
Not sure how to use mapply

test<-vector("list", 5)
lll<-rle(a)
for (i in seq_along(lll$lengths)) test[[i]] <- rep(paste("hello", 
lll$values[i]), lll$lengths[i])
The
all
That is rather vague description. Does those files have some structure? 
How do you know the variable k?

Loops are not so ineffective if you use them for what they are good and if 
you do not expand the object within loop. See R-Inferno from P.Burns.

Regards
Petr
wrote:
elements
be nice
http://www.R-project.org/posting-guide.html
#
Well, I'm not Prof. Ripley, but the answer is: Look at the code.
seq_len, seq.int, and seq_along call Primitives, which are implemented
in C, and therefore MUCH faster than seq(), which is implemented as
pure R code (and is also a generic, so requires method dispatch).
Though for small n (up to a few thousand, say), it probably doesn't
make much difference.(Here, to be corrected by Prof. Ripley is
needed).

-- Bert

On Tue, Jan 25, 2011 at 2:22 AM, Ivan Calandra
<ivan.calandra at uni-hamburg.de> wrote:

  
    
#
Now I understand what the difference between a primitive and a 
non-primitive!
Thanks for the clarification!
Ivan

Le 1/25/2011 18:03, Bert Gunter a ?crit :

  
    
#
On Tue, Jan 25, 2011 at 08:58:31AM +0000, Prof Brian Ripley wrote:
[...]
Thank you for pointing out the functions seq_len(), seq_along() and
seq.int(). These functions are primitive and faster, as others already
mentioned. Using replicate(), i obtained on my computer a speed up by a
factor between 5 and 7 for k <= 20 and there is a remarkable speed up
also for larger k. The function seq.int() is more general than the other
two. In particular, it can generate also a decreasing sequence.

Petr Savicky.