Is the function initFields not a good way to initialize arbitrary fields of a reference class? If not what would you suggest? And how could I handle the a field of type "ANY", because for the string "ANY" I cant do a call like do.call(fields[[i]],list())

Part.initFields<-function(args){
  argNames <- names(args)
  fields<-.self$getRefClass()$fields()
  fieldNames <- names(fields)
  for(i in seq_along(fields)){
     var <- if(is.null(args[[fieldNames[i]]])) do.call(fields[[i]],list())
            else do.call(paste("as.",fields[[i]],sep=""),list(args[[fieldNames[i]]]))
     assign(fieldNames[[i]], var, attr(.self, ".xData"))
   }
 }

Part.initialize<-function(...){
  args<-list(...)
  .self$initFields(args)
  .self
}

Part<-setRefClass(Class = "Part"
                 ,fields = c(var1 = "numeric", var2 = "character")
                 ,methods = list(initialize=Part.initialize
                                ,initFields=Part.initFields))

part<-Part$new(var1=1)
有帮助吗?

解决方案

Use the initialize method to coerce arguments. Explicitly exclude coercions that you do no wish to perform. Coerce using as(x, "class") instead of trying to construct function names from character strings. Do not re-implement initFields.

Part <- setRefClass(Class = "Part",
    fields=c(var0 = "ANY", var1 = "numeric", var2 = "character"),
    methods=list(
      initialize=function(...) {
          args <- list(...)
          map <- .self$getRefClass()$fields(); map <- map[map != "ANY"]
          idx <- names(args) %in% names(map)
          args[idx] <- Map(as, args[idx], map[names(args)[idx]])
          do.call(.self$initFields, args)
      }))

Simple test cases

Part()
Part(var2=1:3)
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top