2015-04-14 18 views
5

Tôi có một loạt các chức năng nhỏ tạo ra các chuỗi ngẫu nhiên tương tự như rnorm hoặc sample. Tất cả các hàm này đều có các đối số chung, vì mục đích đơn giản, hãy nói một đối số chung là n. Tôi muốn thực hiện một hàm lớn hơn (chức năng) có số n và đối số cộng với ... có thể là bất kỳ chức năng nhỏ nào. Hàm meta này đánh giá các hàm nhỏ với tập hợp n nếu chúng có đối số này. đây là một ví dụ:Cho đối số thiếu phổ biến trong chức năng

## CHỨC NĂNG Little

fun1 <- function(n, x = 1:10) sample(x, n, TRUE) 
fun2 <- function(n, x = LETTERS) sample(x, n, TRUE) 
fun3 <- function(n, x = 50) rnorm(n, x) 
fun4 <- function(n, x = 100, y = 10) rnorm(n, x, y) 

CHỨC NĂNG (META CHỨC NĂNG)

combiner <- function(n, ...){ 

## Where the magic needs to happen. Set n for `fun1` `fun2` and `fun4` 
## evaluate all these functions 

} 

## Here we pass `n = 6` 
combiner(
    6, 
    fun1(), 
    fun2, 
    rnorm(), 
    fun4(y=8) 
) 

Tôi muốn nó để đánh giá chức năng ngay cả khi họ đang thiếu () như là trường hợp với fun2 ở trên nhưng điều này là nhiều hơn một nicety. Tôi nghĩ điều này là có thể bởi vì các đường ống magrittr có thể làm được điều này.

## MONG MUỐN OUTPUT

list(
    fun1(6), 
    fun2(6), 
    rnorm(6), 
    fun4(6, y=8) 
) 


## OUTPUT IS SEED DEPENDANT 
## [[1]] 
## [1] 2 1 6 6 1 1 
## 
## [[2]] 
## [1] "V" "Z" "A" "F" "F" "G" 
## 
## [[3]] 
## [1] -0.91932716 -0.05833169 1.75440750 2.19959565 -0.11145315 1.32216601 
## 
## [[4]] 
## [1] 107.48747 89.55798 93.15771 111.32380 100.82104 104.07829 

Trả lời

6

Đây là cách tôi muốn tiếp cận này:

combiner <- function(n, ...) { 
    ## Capture the unevaluated calls and symbols passed via ... 
    ll <- as.list(substitute(list(...)))[-1] 
    ## Process each one in turn 
    lapply(ll, FUN = function(X) { 
     ## Turn any symbols/names into calls 
     if(is.name(X)) X <- as.call(list(X)) 
     ## Add/replace an argument named n 
     X$n <- n 
     ## Evaluate the fixed up call 
     eval(X) 
    }) 
} 

combiner(6, fun1(), fun2, rnorm(), fun4(y=8)) 
# [[1]] 
# [1] 3 8 9 7 4 7 
# 
# [[2]] 
# [1] "Z" "M" "U" "A" "Z" "U" 
# 
# [[3]] 
# [1] 0.6100340 -1.0323017 -0.6895327 1.2534378 -0.3513120 0.3116020 
# 
# [[4]] 
# [1] 112.31979 91.96595 79.11932 108.30020 107.16828 89.46137 
+0

tôi đã rối tung mọi cách mà nhưng không bao giờ nhận được gần that.I've bao giờ sử dụng ' as.call' trước đây. Cảm ơn bạn. –

Các vấn đề liên quan