[R] sapply Call Returning " the condition has length > 1" Error

Alex Zhang alex.zhang at ymail.com
Wed Dec 28 00:29:02 CET 2011


Jeff,

Could you please tell me which part of the guide that I didn't follow?

I provide a piece of code that can run in R, producing the problem and I also provided my results. 

Other people wanted to help me to learn more so asked me about more details. I replied very carefully explaining that i had provided all relevant information.

Jeff, before you response, did you read any of previous posts?

Sent from my iPhone

On Dec 27, 2011, at 6:19 PM, Jeff Newmiller <jdnewmil at dcn.davis.ca.us> wrote:

> I suggest you (re-?)read the posting guide. Proper etiquette on this list is to provide a fully self-contained ("reproducible") example that demonstrates your problem. You are free to supply an alternate to your actual function as long as it illustrates your problem and you can deal with the re-substitution on your own.
> ---------------------------------------------------------------------------
> Jeff Newmiller                        The     .....       .....  Go Live...
> DCN:<jdnewmil at dcn.davis.ca.us>        Basics: ##.#.       ##.#.  Live Go...
>                                      Live:   OO#.. Dead: OO#..  Playing
> Research Engineer (Solar/Batteries            O.O#.       #.O#.  with
> /Software/Embedded Controllers)               .OO#.       .OO#.  rocks...1k
> --------------------------------------------------------------------------- 
> Sent from my phone. Please excuse my brevity.
> 
> Alex Zhang <alex.zhang at ymail.com> wrote:
> 
>> John,
>> 
>> Thank you for your comment.�
>> 
>> There is no secret. But the actual function I need to call is rather
>> irrelevant.�However don't take it as the "abs" function. If you like to
>> know, it is a function that converts 4 kinds of old ids from several
>> old database tables into a new id in a new database. Again, I don't
>> think providing�such detail is better than saying MyDummyFunc maps a
>> number into a number but doesn't work�with vectors.
>> 
>> All I need to do, is to call DummyFunc for every element in a column of
>> a data.frame and returns�the resulted vector. But, I cannot change
>> DummyFunc. Correct me if I am wrong: this is rather�common in a
>> group�collaboration enviroment. Person A may be responsible for writing
>> a function and person B who needs to use that function cannot or better
>> not change it.
>> 
>> Obviously, I could write a loop. Michael in a previous post suggested
>> using vectorize which works perfectly. As a newbie of R, I would wish
>> to learn more ways to achieve my goal (sorry, it automatically involves
>> "how" not just "what" ;). Is there a way using�a "*apply" function to
>> do it where * stands for any function.
>> 
>> Thanks a lot!�
>> 
>> 
>> ________________________________
>> From: John Fox <jfox at mcmaster.ca>
>> To: 'Alex Zhang' <alex.zhang at ymail.com> 
>> Cc: r-help at r-project.org 
>> Sent: Tuesday, December 27, 2011 4:06 PM
>> Subject: RE: [R] sapply Call Returning " the condition has length > 1"
>> Error
>> 
>> Dear Alex,
>> 
>>> -----Original Message-----
>>> From: Alex Zhang [mailto:alex.zhang at ymail.com]
>>> Sent: December-27-11 3:34 PM
>>> To: John Fox
>>> Cc: r-help at r-project.org
>>> Subject: Re: [R] sapply Call Returning " the condition has length >
>> 1"
>>> Error
>>> 
>>> John,
>>> 
>>> Thanks for the pointers.
>>> 
>>> The DummyFunc is just a made-up example. The true function I need to
>>> use is more complicated and would be distractive to include.
>> 
>> You'll probably get a better answer if you don't keep what you want to
>> do a
>> secret.
>> 
>>> 
>>> Do you mean that sapply would take columns in the input data.frame
>> and
>>> feed them into "FUN" as "whole" vectors? That explains the behavior.
>> 
>> Yes. As I said, a data frame is a list of columns, so FUN is called
>> with
>> each column as its argument.
>> 
>>> Is there an "*apply" function that will fee elements of the input
>>> data.frame into "FUN" instead of whole columns? Thanks.
>> 
>> I'm afraid that I don't know what you mean. Do you want to deal with
>> the
>> columns of the data frame separately (in general, they need not all be
>> of
>> the same class), and within each column, apply a function separately to
>> each
>> element? You could nest calls to lapply() or sapply(), as in
>> 
>> sapply(D, function(DD) sapply(DD, abs))
>> 
>> assuming, of course, that D is an entirely numeric data frame. But in
>> this
>> case,
>> 
>> abs(as.matrix(D))
>> 
>> would be more sensible, and using sapply() like this isn't necessarily
>> better than a loop. Again, not knowing what you want to do makes it
>> hard to
>> suggest a solution.
>> 
>> Best,
>> John
>> 
>>> 
>>> ________________________________
>>> 
>>> From: John Fox <jfox at mcmaster.ca>
>>> To: 'Alex Zhang' <alex.zhang at ymail.com>
>>> Cc: r-help at r-project.org
>>> Sent: Tuesday, December 27, 2011 3:10 PM
>>> Subject: RE: [R] sapply Call Returning " the condition has length >
>> 1"
>>> Error
>>> 
>>> Dear Alex,
>>> 
>>>> -----Original Message-----
>>>> From: r-help-bounces at r-project.org [mailto:r-help-bounces at r-
>>>> project.org] On Behalf Of Alex Zhang
>>>> Sent: December-27-11 2:14 PM
>>>> To: r-help at r-project.org
>>>> Subject: [R] sapply Call Returning " the condition has length > 1"
>>>> Error
>>>> 
>>>> Dear all,
>>>> 
>>>> Happy new year!
>>>> 
>>>> I have a question re using sapply. Below is a dummy example that
>>> would
>>>> replicate the error I saw.
>>>> 
>>>> ##Code Starts here
>>>> DummyFunc <- function(x) {
>>>> 
>>>> if (x > 0) {
>>>> return (x)
>>>> } else
>>>> {
>>>> return (-x)
>>>> }
>>>> 
>>>> }
>>>> 
>>>> Y = data.frame(val = c(-3:7))
>>>> sapply(Y, FUN = DummyFunc)
>>>> ##Code ends here
>>>> 
>>>> When I run it, I got:
>>>> � � � val
>>>> � [1,]� 3
>>>> � [2,]� 2
>>>> � [3,]� 1
>>>> � [4,]� 0
>>>> � [5,]� -1
>>>> � [6,]� -2
>>>> � [7,]� -3
>>>> � [8,]� -4
>>>> � [9,]� -5
>>>> [10,]� -6
>>>> [11,]� -7
>>>> Warning message:
>>>> In if (x > 0) { :
>>>> � the condition has length > 1 and only the first element will be
>>> used
>>>> 
>>>> The result is different from what I would expect plus there is such
>>> an
>>>> error message.
>>> 
>>> This is a warning, not really an error message. A data frame is
>>> essentially a list of variables (columns), and sapply() applies its
>>> FUN argument to each list element, that is, each variable -- the one
>>> variable val in your case.
>>> That produces a warning because val > 0 is a vector of 11 elements,
>>> and the first comparison, 3 > 0, which is TRUE, controls the result.
>>> 
>>>> 
>>>> I guess if the DummyFunc I provided is compatible with vectors, the
>>>> problem would go away. But let's suppose I cannot change DummyFunc.
>>> Is
>>>> there still a way to use sapply or alike without actually writing a
>>>> loop? Thanks.
>>> 
>>> Well, you could just use
>>> 
>>>> abs(Y$val)
>>> [1] 3 2 1 0 1 2 3 4 5 6 7
>>> 
>>> but I suppose that you didn't really want to write your own version
>> of
>>> the absolute-value function as something more than an exercise.
>>> 
>>> An alternative is
>>> 
>>>> with(Y, ifelse(val > 0, val, -val))
>>> [1] 3 2 1 0 1 2 3 4 5 6 7
>>> 
>>> I hope this helps,
>>> John
>>> 
>>> --------------------------------
>>> John Fox
>>> Senator William McMaster
>>> �  Professor of Social Statistics
>>> Department of Sociology
>>> McMaster University
>>> Hamilton, Ontario, Canada
>>> http://socserv.mcmaster.ca/jfox
>>> 
>>> 
>>> 
>>>> 
>>>> - Alex
>>>> � �  [[alternative HTML version deleted]]
>>> 
>>> 
>>> 
>>> 
>>    [[alternative HTML version deleted]]
>> 
>> ______________________________________________
>> R-help at r-project.org mailing list
>> https://stat.ethz.ch/mailman/listinfo/r-help
>> PLEASE do read the posting guide
>> http://www.R-project.org/posting-guide.html
>> and provide commented, minimal, self-contained, reproducible code.
> 



More information about the R-help mailing list