开发者

How to pass function arguments to within?

I wonder how I can pass arguments of some function to a subpart of the function that uses with / within. e.g.:

  myfunction <- function(dataframe开发者_开发问答,col1,col2){

  res <- within(dataframe, somenewcol <-paste(col1,"-","col2",sep=""))

  return(res)


  }

where col1 and col2 are columns contained in the dataframe. What´s the correct way to pass the arguments col1 and col2 to the within expression? When I just try to use it, i get :

Error in paste(col1, "-", , : object 'Some_passed_col' not found

Here´s an example:

   dataset <- data.frame(rnorm(20),2001:2020,rep(1:10,2))
   names(dataset) <- c("mydata","col1","col2")

   myfunction <- function(dataframe,arg1,arg2){
   res <- with(dataframe, onesinglecol <- paste(arg1,"-","arg2",sep=""))
   return(res)



   }
# call function
myfunction(dataset,col1,col2)

EDIT:

the following works for me now, but I cannot completely understand why... so any further explanation is appreciated:

 myfunction(dataset,arg1="col1",arg2="col2")

if I adjust

res <- with(dataframe, onesinglecol <- paste(get(arg1),"-",get(arg2),sep=""))


Try

   myfunction <- function(dataframe,arg1,arg2){
   dataframe["onesinglecol"] <- dataframe[[arg1]] -dataframe[[arg2]]
   return(dataframe) 
   }

And call it with character-valued column names rather than object names that are nowhere defined:

myfunction(dataset,"col1","col2")
       mydata col1 col2 onesinglecol
1   0.6834402 2001    1         2000
2   1.6623748 2002    2         2000
3  -0.5769926 2003    3         2000  .... etc


I think this is done via the ... directive: E.g.:

myfunction <- function(dataframe, ...){

  var <- anotherfunction( arg1= 1, arg2 = 2 , ...)
  return(var)
}

... is a placeholder for additional arguments passed through to "anotherfunction".


You are missing the fact that col1 and col2 do not exist in dataframe (from your) nor in the user workspace.

Basically, with() and within() work like this:

> foo <- 10
> bar <- data.frame(FOO = 10)
> FOO + foo
Error: object 'FOO' not found
> with(bar, FOO + foo)
[1] 20

In the first case, FOO was not found as it is inside bar. In the second case, we set up an environment within which our expression is evaluated. Inside that environment FOO does exist. foo is also found in the workspace.

In your first example (please don't edit error messages etc, show us exactly what code you ran and what error was produced) either one col1 or col2 didn't exist in the environment created within which your expression was evaluated.

Further, you appear to want to store in col1 and col2 the name of a column (component) of your dataframe. DWin has shown you one way to use this information. An alternative maintaining the use of within() is to use get() like this:

res <- within(dataframe, somenewcol <- paste(get(col1), "-", get(col2), sep=""))

Why this works, as per your extra edit and quandary, is that get() returns the object named by it's first argument. get("foo") will return the object named foo (continuing from my example above):

get("foo") ## finds foo and returns it 1 10

In your example, you have a data frame with names inter alia "col1" and "col2". You changed your code to get(arg1) (where arg1 <- "col1"), where you are asking get() to return the object with name "col1" from the evaluation environment visible at the time your function is being evaluated. As your dataframe contained a col1 component, which was visible because within() had made it available, get() was able to find an object with the required name and include it in the expression.

But at this point you are trying to jump through too many hoops because your questions haven't been specific. I presume you are asking this because of my answer here to your previous Q. That answer suggested a better alternative than attach(). But you weren't clear there what some arguments were or what your really wanted to do. If I had known now what you really wanted to do then I would have suggested you use DWin's Answer above.

You seem to not want to hard code the column/component names. If you could hard code, this would be the solution:

res <- within(dataframe, somenewcol <- paste(col1, "-", col2, sep = ""))

But seeing as you don't want to hard code you need a get() version or DWin's solution.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜