2

作成した関数で使用する一連のパラメーターを作成して返す関数を作成したいと思いますmySimulation。今までは、基本的に、例えば mySimulation(parm1 = 3, parm2 = 4). (1) 実際のバージョンでは、パラメーターの数が扱いにくくなっており、(2) 使用しているさまざまなモデルを生成するパラメーターのさまざまな組み合わせを追跡したいため、これは最適ではありません。createParmsそこで、このトリックを実行するために (以下に示す最小限のバージョンを)書きました。しかし、私の全体的なアプローチはとても不格好に思えます。すべての統計学者が R を使用しているため、私の問題を処理するためのより標準的な方法があると確信しています...そうですか?

createParms <- function(model = "default", ...) {
  # Returns a list `parms` of parameters which will then be used in  
  # mySimultation(parms)
  #
  # Args:
  #   model: ["default" | "mymodel"] character string representation of a model 
  #          with known parameters
  #   ...: parameters of the existing `model` to overwrite.
  #        if nothing is supplied then the model parameters will be left as is. 
  #        passed variables must be named.
  #        e.g., `parm1 = 10, parm2 = 20` is good. `10, 20` is bad. 
  #
  # Returns:
  #   parms: a list of parameters to be used in mySimulation(parms)
  #          
  parms.names <- c("parm1", "parm2")
  parms <- vector(mode = "list", length = length(parms.names))
  names(parms) <- parms.names
  overwrite <- list(...)
  overwrite.names <- names(overwrite)
  if (model == "default") {
    parms$parm1 <- 0
    parms$parm2 <- 0
  } else if (model == "mymodel") {
      parms$parm1 <- 1
      parms$parm2 <- 2
  } 
  if (length(overwrite) != 0) {
    parms[overwrite.names] <- overwrite
  }
  return(parms)
}
4

2 に答える 2

2

各モデルで使用するパラメータの組み合わせが分かっている場合は、以下のようにモデル名とパラメータのデータフレームを作成した方が良いと思います

# create a data frame with model names and parameters
# NOTE: i am assuming all models have equal number of parameters
# if they are unequal, then store as list of models

model = c('default', 'mymodel');
parm1 = c(0.5, 0.75);
parm2 = c(1, 2);

models.df = data.frame(model, parm1, parm2)

mySimulation 関数に引数として渡すことで、任意のモデルをシミュレートできるようになりました。ダミーのシミュレーション例を使用しましたが、これをコードに置き換えることができます。

# function to run simulation based on model name

mySimulation = function(model = 'default'){

  # find row corresponding to model of interest
  mod.row = match(model, models.df$model)

  # extract parameters corresponding to model
  parms   = models.df[mod.row, -1]

  # run dummy simulation of drawing normal random variables
  sim.df  = rnorm(100, mean = parms[,1], sd = parms[,2])
  return(sim.df)

}

すべてのシミュレーションを 1 ステップで実行したい場合は、優れたplyrパッケージを使用して呼び出すことができます。

library(plyr)
sim.all = ldply(models.df$model, mySimulation)

llply各シミュレーションが異なる数の値を返す場合は、代わりに関数を使用できますldply

シミュレーションの戻り値とその動作の詳細に関する詳細情報を提供すると、このコードを簡単に調整して、必要なものを取得できます。

これがうまくいくかどうか教えてください

于 2011-04-16T20:19:42.913 に答える
1

シミュレーション関数が常に同じ引数のセットを取る場合、それらをデータ フレームに格納する Ramnath のアプローチが最適です。への変数入力のより一般的なケースではmySimulation、入力の各セットをリストに格納する必要があります。おそらく、いくつかのシミュレーションを実行するためにリストのリストを使用します。

関数の背後にあるアイデアcreateParmsは適切に見えます。コードを少し単純化できます。

createParms <- function(model = "default", ...) 
{
  #default case
  parms <- list(
    parm1 = 0,
    parm2 = 0
  )

  #other special cases
  if(model == "mymodel")
  {
    parms <- within(parms,     
    {
      parm1 <- 1
      parm2 <- 2
    })  
  }

  #overwrite from ...
  dots <- list(...)
  parms[names(dots)] <- dots

  parms
}

これを次のようにテストします。

createParms()
createParms("mymodel")  
createParms("mymodel", parm2 = 3)

do.call次のように、シミュレーションを実行するのに役立つ場合があります。

do.call(mySimulation, createParms())

編集:あなたのために何do.callをしますか

あなたが持っている場合parms <- createParms()

do.call(mySimulation, parms)

と同じです

with(parms, mySimulation(parm1, parm2))

主な利点は、渡す各パラメーターを詳しく説明する必要がないことですmySimulation(または、パラメーターをリスト形式で受け入れるようにその関数を変更する必要はありません)。

于 2011-04-18T11:10:06.697 に答える