在R中调用replicate时使用与不使用%>%管道为何输出不同?
关于replicate和管道符结合生成重复随机字符串的问题
问题场景
需要生成包含20个随机字符串的字符向量:
- 单条生成代码:
sample(x = c(letters, LETTERS), size = sample.int(100, 1), replace = T) %>% paste0(collapse = ""),能正常生成单个随机字符串 - 直接将这段代码作为
replicate的expr参数:replicate(n=20, expr=sample(x = c(letters, LETTERS), size = sample.int(100, 1), replace = T) %>% paste0(collapse = "")),输出20个不同的随机字符串,符合预期 - 但通过管道符把单条生成代码传给
replicate:sample(x = c(letters, LETTERS), size = sample.int(100, 1), replace = T) %>% paste0(collapse = "") %>% replicate(n=20, expr=., simplify="array"),得到的20个元素完全相同
问题原因
这是管道符和replicate的执行逻辑差异导致的:
- 用管道传值时,左边的随机字符串生成代码会先执行完成,生成一个固定的字符串,然后这个现成的字符串才被传给
replicate的expr参数。replicate拿到的是个固定值,自然只会重复输出它20次,不会重新执行生成逻辑。 - 而直接把生成代码写在
replicate的expr参数里时,replicate会在每一次循环中重新运行这段代码,所以每次都能生成新的随机字符串。
解决方法
如果一定要用管道实现,需要把生成逻辑包装成匿名函数,让replicate每次调用函数生成新字符串:
# 写法1:用匿名函数包装 (function() { sample(x = c(letters, LETTERS), size = sample.int(100, 1), replace = T) %>% paste0(collapse = "") }) %>% replicate(n=20, expr=., simplify="array") # 写法2:用公式简化 ~sample(x = c(letters, LETTERS), size = sample.int(100, 1), replace = T) %>% paste0(collapse = "") %>% replicate(n=20, expr=., simplify="array")
内容的提问来源于stack exchange,提问作者a.sa.5969
相关产品推荐
相关产品推荐

