ハドレーの「Advanced R」では、ファンクションプログラミングと「ファンクション演算子」の可能なアプリケーションについて簡単に説明します。しかし、私の心配は、これらのコードがどのように単純化されているかを完全には理解していないか、他のソリューションを使用して悪い習慣に従わないことです。ファンクションオペレータとファンクションラッピングR
入力が関数であることを期待する演算子を作成する代わりに、式を引数として受け取り、(呼び出される必要のある関数ではなく)完全な出力を返すラッパーを作成します。例:
# function operator
delay_by <- function(delay, f) {
function(...) {
Sys.sleep(delay)
f(...)
}
}
# simple wrapper
delay_by2 <- function(expr, delay) {
Sys.sleep(delay)
eval(expr)
}
delay_by(1, sqrt)(2)
delay_by2(sqrt(2), 1)
operator <- delay_by(1, sqrt)
wrapper <- function(x) delay_by2(sqrt(x), 1)
operator(2)
wrapper(2)
このアプローチでは、機能(サプリーなど)に入力してメモを適用することができます。また、%>%
の配管もサポートしています。
lapply(1:10, function(x) sqrt(x) %>% delay_by2(1))
このソリューションの潜在的な欠点は、それが機能の状態を維持する変数を格納するための永続的な実行環境を作成していないということですが、これらは<<- new.env()
で明示的に作成することができます。
私のアプローチが劣っていると考える理由はありますか?私は不要なネスティングを避けようとしています。
評価方法では、プリコホール処理が許可されていません。これは、コード・インジェクション・シナリオでも使用される可能性があります。しかし、これらは非生産コードに対するマイナーな懸念事項です。 –
安全性の問題について - 関数演算子がチェックを実行しない場合、与えられた関数がホワイトリストに載っている場合、 'eval()'には何のメリットもないと言っていますか? – mjktfw
実際、あなたが 'eval(,,) 'を使用していて、' eval(parse(..))ではない場合、多分私の反対は成立しません。 –