[R] Relase positive with log and zero of negative with 0
Martin Maechler
maechler at stat.math.ethz.ch
Wed Nov 18 09:27:32 CET 2009
>>>>> "PE" == Peter Ehlers <ehlers at ucalgary.ca>
>>>>> on Mon, 16 Nov 2009 06:55:00 -0700 writes:
PE> David Winsemius wrote:
>>
>> On Nov 15, 2009, at 10:18 AM, <rkevinburton at charter.net> wrote:
>>
>>> This is a very simple question but I couldn't form a site search
>>> quesry that would return a reasonable result set.
>>>
>>> Say I have a vector:
>>>
>>> x <- c(0,2,3,4,5,-1,-2)
>>>
>>> I want to replace all of the values in 'x' with the log of x.
>>> Naturally this runs into problems since some of the values are
>>> negative or zero. So how can I replace all of the positive elements of
>>> x with the log(x) and the rest with zero?
>>
>> > x <- c(0,2,3,4,5,-1,-2)
>> > x <- ifelse(x>0, log(x), 0)
>> Warning message:
>> In log(x) : NaNs produced
>> > x
>> [1] 0.0000000 0.6931472 1.0986123 1.3862944 1.6094379 0.0000000 0.0000000
>>
>> The warning is harmless as you can see, but if you wanted to avoid it,
>> then:
>>
>> > x[x<=0] <- 0; x[x>0] <-log(x[x>0])
>>
>> In the second command, you need to have the logical test on both sides
>> to avoid replacement " out of synchrony."
>>
PE> Here is one more way, somewhat less transparent, motivated
PE> by the examples on the ?ifelse page:
PE> x <- log(ifelse(x > 0, x, 1))
Yes, indeed. And this one pretty clearly demonstrates
that -- from an analytic point of view --
this is really in most cases a "non-sense" transformation:
one and all negative numbers are mapped to zero;
the rest is log transformed:
Look at its graph via
curve(log(ifelse(x > 0, x, 1)), -2, 3)
Rather log(abs(x))
or log(abs(x + eps)) {eps = 1 or eps = 1e-10 or ...}
typically are more useful for what I guess the OP wants the
trafo to use for...
or then, if you think further and want a
- monotone
- continuous and even smooth (once-differentiable)
log-like transformation
then consider using the u.log() function I have written some 13 years ago,
(inspired by coffebreak discussions with Werner Stahel)
available from
install.packages("sfsmisc")
require("sfsmisc")
curve(u.log, -2, 3, col=2)
curve(u.log(x, c=0.5), add=TRUE, col=3)
?u.log
----
Martin Maechler, ETH Zurich
More information about the R-help
mailing list