[Rd] significant digits (PR#9682)
Duncan Murdoch
murdoch at stats.uwo.ca
Tue Jun 3 12:36:44 CEST 2008
pmc1 at cornell.edu wrote:
> I came to report this same bug and found it already in the trash, but
> I slightly disagree with that assessment. If it's not a bug, then
> perhaps it's a feature request. Comments at the end.
>
> On Mon, May 14, 2007, Duncan Murdoch wrote:
>
>>> On 13/05/2007 8:46 PM, scott.wilkinson at csiro.au wrote:
>>>
>>> In the example below round() does not report to the specified number of
>>> digits when the last digit to be reported is zero: Compare behaviour for
>>> 0.897575 and 0.946251. Ditto for signif(). The number of sigfigs is
>>> ambiguous unless the reader knows this behaviour. Is this a bug or
>>> intended behaviour? Is there a work-around?
>>>
>> It's not a bug. It has nothing to do with round(), it is the way R
>> prints numbers by default. If you ask to print 0.90, you'll get
>>
>> [1] 0.9
>>
>> because 0.9 and 0.90 are the same number. If you want trailing zeros to
>> print, you need to specify a format to do that, e.g.
>>
>>
>>> noquote(format(0.9, nsmall=2))
>>>
>> [1] 0.90
>>
>> The noquote stops the "" from printing. You could also use sprintf() or
>> formatC() for more C-like format specifications.
>>
>
> All of those options require you to specify the number of digits after
> the decimal, don't they? Unless sprintf would default to the number of
> decimal places passed to it, but it doesn't:
>
That specification doesn't make sense. There is no "number of decimal
places passed to it". What sprintf() sees below is identical to what it
would see if you called
sprintf("%f", 0.9)
because signif(0.90, digits=2) == 0.9. Those two objects are identical.
> > sprintf("%f",signif(0.90, digits=2))
> [1] "0.900000";
>
> it defaults to 6. Although %g behaves differently,
>
> > sprintf("%g",signif(0.90, digits=2))
> [1] "0.9",
>
> this clearly still isn't the desired behavior.
>
Maybe not what you desired, but certainly reasonable behaviour.
> To continue that vein, the same issue with rounding versus printing
> occurs with vectors:
>
> > sapply(c(1:6),function(a){signif(c(18.423,0.90),digits=a)})
> [,1] [,2] [,3] [,4] [,5] [,6]
> [1,] 20.0 18.0 18.4 18.42 18.423 18.423
> [2,] 0.9 0.9 0.9 0.90 0.900 0.900
>
> Trying to get that and more complicated tables to print the correct
> number of significant digits gets pretty hairy with sprintf(). I could
> be wrong, but I would view the primary purpose of rounding to
> significant digits the printed output of the number. That there
> doesn't seem to be a way to do this without later having to specify
> the number of decimal places would seem to render signif() as it's
> written not particularly useful.
>
> There are two solutions I can think of off the top of my head. The
> first is to create a new data type of a fixed length real number but
> the easier way would be to have a function that returns a string
> something like this:
>
> signif.string <- function(signum,sigdigs){
> left <- nchar(trunc(signum))
> right <- nchar(signum-trunc(signum))-2
> if (abs(signum)<1 | signum<0) {left<-left-1}
> if (right<0) {right<-0}
> if (sigdigs<left) {return(as.character(signif(signum,digits=sigdigs)))}
> else if (sigdigs==left) {return(paste(round(signum),".",sep=""))}
> else if (sigdigs<=left+right) {return(format(signum,digits=sigdigs))}
> else {return(sprintf(paste("%.",sigdigs-left,"f",sep=""),signum))}
> }
>
>
> This is just a skeleton that I think suits my needs for the moment and
> might also cover the original poster's. One for production would need
> to handle scientific notation and would probably want to fix the 5
> round behavior on windows.
>
As far as I know, rounding is fine in Windows:
> round(1:10 + 0.5)
[1] 2 2 4 4 6 6 8 8 10 10
looks okay to me. If you want biased rounding instead (getting 2:11 as
output), simply use trunc(x + 0.5) instead of round(x).
Duncan Murdoch
> Pat Carr
>
> version.string R version 2.7.0 (2008-04-22)
>
> ______________________________________________
> R-devel at r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-devel
>
More information about the R-devel
mailing list