histogram plotting function freezes up R?

208 views
Skip to first unread message

David Faden

unread,
Feb 10, 2009, 3:12:55 PM2/10/09
to ggp...@googlegroups.com
Hi,

I was looking at writing a convenience function for creating
histograms of integer elements (and also provide an example in
response to Hadley's request), but my function seems to lock up R.
Here's the function:

library(ggplot2)
intHist <- function(x, xlab=xlab, main=main) {
d <- data.frame(x=x)
r <- range(x)
print(qplot(x, data=d, breaks=seq(r[1] - 0.5, r[2] + 0.5, by=1),
xlab=xlab, main=main, geom="histogram"))
}

After defining this, in R 2.8.1 with ggplot2 0.8.1 on a MacBook Pro,
executing the following causes R to freeze:

intHist(c(1,1,2,2,2))

Any ideas? Thanks.

David

David Kahle

unread,
Feb 10, 2009, 4:01:20 PM2/10/09
to David Faden, ggp...@googlegroups.com
Hi David -

It seems to me like what you want to do is something like this

x <- sample(10,100, replace = T)
d <- data.frame(x=x)
qplot(x, data = d, geom = 'histogram') +
   scale_x_continuous(breaks = seq(min(x), max(x), 1))

Is there a difference?

Cheers
david.

David Faden

unread,
Feb 10, 2009, 4:46:30 PM2/10/09
to David Kahle, ggp...@googlegroups.com
Hi David :-)

Thank you. I think the only difference is that I want the breaks to be
shifted slightly so that the input values are not on the boundaries of
the intervals. For integer data in particular, I find the plot to be
clearer this way.

Running the same code under R 2.7.2, my function exits with an error
rather than freezing up:

> intHist(c(0,0,0,1,1))
Error in qplot(x, data = d, breaks = seq(r[1] - 0.5, r[2] + 0.5, by = 1), :
promise already under evaluation: recursive default argument
reference or earlier problems?

I found that switching to using the method you described is still
freezing up R 2.8.1 and also produces the above error message in R
2.7.2. (I think they are equivalent under the covers.)

intHist <- function(x, xlab=xlab, main=main) {
d <- data.frame(x=x)

print(qplot(x, data=d, xlab=xlab, main=main, geom="histogram") +
scale_x_continuous(breaks = seq(min(x), max(x), 1)))
}

> intHist(c(0,0,0,1,1))
Error in qplot(x, data = d, xlab = xlab, main = main, geom = "histogram") :
promise already under evaluation: recursive default argument
reference or earlier problems?

Sounds kind of funky.

David

David Kahle

unread,
Feb 10, 2009, 5:40:05 PM2/10/09
to David Faden, ggp...@googlegroups.com
Hi David -

On Feb 10, 2009, at 3:46 PM, David Faden wrote:

Hi David :-)

Thank you. I think the only difference is that I want the breaks to be
shifted slightly so that the input values are not on the boundaries of
the intervals. For integer data in particular, I find the plot to be
clearer this way.

You're right!  I only noticed after looking at it that they are shifted.  Good eye.



Running the same code under R 2.7.2, my function exits with an error
rather than freezing up:

intHist(c(0,0,0,1,1))
Error in qplot(x, data = d, breaks = seq(r[1] - 0.5, r[2] + 0.5, by = 1),  :
 promise already under evaluation: recursive default argument
reference or earlier problems?


One problem which was killing it was how you defaulted xlab - it needs to be xlab = 'xlab'  in quotes (the axis label's a character string, see below).  Otherwise, when it tries to evoke it, it will start looking for the variable xlab, and it won't find it.  It was making it hang on my computer; probably the same on yours. 


I found that switching to using the method you described is still
freezing up R 2.8.1 and also produces the above error message in R
2.7.2. (I think they are equivalent under the covers.)

intHist <- function(x, xlab=xlab, main=main) {
d <- data.frame(x=x)
print(qplot(x, data=d, xlab=xlab, main=main, geom="histogram") +
scale_x_continuous(breaks = seq(min(x), max(x), 1)))
}

intHist(c(0,0,0,1,1))
Error in qplot(x, data = d, xlab = xlab, main = main, geom = "histogram") :
 promise already under evaluation: recursive default argument
reference or earlier problems?


One fix to do what you want is to change the integers to factors.  I've tried this and it seems to do just what you want on my computer.  Let me know if it's what you're looking for.

x <- sample(10,100, replace = T
intHist <- function(x, xlab = 'x', main = '') {
  d <- data.frame(x=factor(x))
  ggplot(aes(x=x), data = d) + 
    stat_bin(breaks = seq(min(x), max(x), 1), width = .5) +
    scale_x_discrete(xlab) + 
    opts(title = main)
}   
intHist(x)  
intHist(x, xlab = 'text x', main = 'test main')  

Cheers

David Kahle

unread,
Feb 10, 2009, 6:02:25 PM2/10/09
to David Faden, ggplot2
Even easier -

qplot(factor(x), geom = 'histogram', xlab = 'x axis', main = 'main
title')

That way you should be able to use pretty much whatever you want as
easily as possible. :)

david.

David Faden

unread,
Feb 10, 2009, 7:12:39 PM2/10/09
to David Kahle, ggplot2
Oh, duh! Thank you! Sorry for hitting the list with my silly R error.
(I think I may be better off keeping the input values as numeric in
order to deal with the case of breaks in the sequence of values, eg,
c(1,1,5,5,5,100), but thank you for instructive code. I have learned
something useful from it.)

David

Reply all
Reply to author
Forward
0 new messages