R 记忆自定义函数并将其矢量化

R 记忆自定义函数并将其矢量化,r,vectorization,memoization,R,Vectorization,Memoization,我想知道如何在R中矢量化和记忆自定义函数 我的思维方式与R的运作方式不一致。所以,我很高兴 欢迎链接到好的阅读材料。例如,R地狱是一个很好的例子 资源,但这无助于找出R中的备忘录 更一般地说,您能否为备忘录 或者R.cache包 我找不到关于这个问题的任何其他讨论。搜索 r-bloggers.com上的“备忘录”或“备忘录”返回零结果。搜索 对于那些关键字,在不返回帮助 讨论。我通过电子邮件发送了邮件列表,但没有收到完整的邮件 回答 我不仅仅对记忆GC函数感兴趣,而且我知道 生物导体和各种封装

我想知道如何在R中矢量化和记忆自定义函数 我的思维方式与R的运作方式不一致。所以,我很高兴 欢迎链接到好的阅读材料。例如,R地狱是一个很好的例子 资源,但这无助于找出R中的备忘录

更一般地说,您能否为
备忘录
或者
R.cache

我找不到关于这个问题的任何其他讨论。搜索 r-bloggers.com上的“备忘录”或“备忘录”返回零结果。搜索 对于那些关键字,在不返回帮助 讨论。我通过电子邮件发送了邮件列表,但没有收到完整的邮件 回答

我不仅仅对记忆GC函数感兴趣,而且我知道 生物导体和各种封装 在那里可以买到

以下是我的数据:

seqs <- c("","G","C","CCC","T","","TTCCT","","C","CTC")
它的工作原理是:

> GC('')
[1] NA
> GC('G')
[1] 100
> GC('GAG')
[1] 66.66667
> sapply(seqs, GC)
                  G         C       CCC         T               TTCCT           
       NA 100.00000 100.00000 100.00000   0.00000        NA  40.00000        NA 
        C       CTC 
100.00000  66.66667
我想把它记下来。然后,我想把它矢量化

显然,我使用
回忆录
R.cache
R包:

> system.time(dummy <- sapply(rep(seqs,100), GC))
   user  system elapsed
  0.044   0.000   0.054
>
> library(memoise)
> GCm1 <- memoise(GC)
> system.time(dummy <- sapply(rep(seqs,100), GCm1))
   user  system elapsed
  0.164   0.000   0.173
>
> library(R.cache)
> GCm2 <- addMemoization(GC)
> system.time(dummy <- sapply(rep(seqs,100), GCm2))
   user  system elapsed
 10.601   0.252  10.926
至少我知道了如何矢量化:

> GCv <- Vectorize(GC)
> GCv(seqs)
                  G         C       CCC         T               TTCCT           
       NA 100.00000 100.00000 100.00000   0.00000        NA  40.00000        NA 
        C       CTC 
100.00000  66.66667 
GCv GCv(序号) G C CCC T TTCCT NA 100.00000100.00000100.000000.00000 NA 40.00000 NA C反恐委员会 100.00000 66.66667 相关stackoverflow帖子:


这并没有明确回答您的问题,但此函数比您的函数快约4倍

GC2 <- function(s) {
  if(!is.character(s)) stop("'s' must be character")
  n <- nchar(s)
  m <- gregexpr('[GCSgcs]', s)
  len <- sapply(m, length)
  neg <- sapply(m, "[[", 1)
  len <- len*(neg > 0)
  len/n
}

GC2虽然这不会让你在通话中进行记忆,但如果有相当多的重复,你可以使用因子使单个通话更快。例如,使用Joshua的GC2(尽管我必须删除fixed=T才能使其工作):


GC2是否有任何特殊原因使您忽略了
nchar
gregexpr
已经矢量化的事实?在我的系统(x86_64 linux gnu R 2.15.0)上,您的功能慢了约3倍。我正在这样测试速度:
system.time(sapply(rep(seqs,1000),GC))
得到0.418秒<代码>系统时间(sapply(rep(seqs,1000),GC2))
得到1.401秒。@KamilSlowikowski这是因为您使用了错误的函数。Joshua对其进行了矢量化,因此您应该将其与
GC2(rep(seqs,1000))
进行比较,在这种情况下,它确实快了~4倍。@KamilSlowikowski,尽管我认为他不是有意设置
fixed=TRUE
。事实上,设置
fixed=t
会导致所有
[[1]]
元素都是
-1
。乔舒亚,谢谢你的密码!现在我知道了如何从列表中的每个项目中提取一个元素,
1*TRUE==1
1*FALSE==0
。我现在觉得自己很傻,因为意识到
nchar
substr
可以处理项目的向量(“列表”),特别是因为帮助
?nchar
明确说明了这一点。@joran:谢谢你指出这一点。这是我测试的一部分,因为
?gregexpr
说使用
fixed=TRUE
可以更快。。。但它不应该出现在我的答案中。这太棒了。非常感谢。回忆录将为我节省相对较少的时间。
> GCv <- Vectorize(GC)
> GCv(seqs)
                  G         C       CCC         T               TTCCT           
       NA 100.00000 100.00000 100.00000   0.00000        NA  40.00000        NA 
        C       CTC 
100.00000  66.66667 
GC2 <- function(s) {
  if(!is.character(s)) stop("'s' must be character")
  n <- nchar(s)
  m <- gregexpr('[GCSgcs]', s)
  len <- sapply(m, length)
  neg <- sapply(m, "[[", 1)
  len <- len*(neg > 0)
  len/n
}
GC2 <- function(s) {
  if(!is.character(s)) stop("'s' must be character")
  n <- nchar(s)
  m <- gregexpr('[GCSgcs]', s)
  len <- sapply(m, length)
  neg <- sapply(m, "[[", 1)
  len <- len*(neg > 0)
  100.0 * len/n
}
GC3 <- function(s) {
  x <- factor(s)
  GC2(levels(x))[x]
}

system.time(GC2(rep(seqs, 50000)))
# user  system elapsed 
# 8.97    0.00    8.99 
system.time(GC3(rep(seqs, 50000)))
# user  system elapsed 
# 0.06    0.00    0.06