2012-11-20 33 views
6

假設我有載體aR:從數據計數生成柱狀圖

c(1, 6, 2, 4.1, 1, 2) 

和計數矢量b

c(2,3,2,1,1,0) 

我想產生矢量c

c(1, 1, 6, 6, 6, 2, 2, 4.1, 1) 

致電:

hist(c) 

我該如何構建c,或者有沒有辦法直接從ab生成直方圖?請注意0​​中的重複項以及不等的間距。

需要矢量化解決方案。 ab對於lapply和朋友來說太大了。

回答

10

?rep

> rep(a, b) 
[1] 1.0 1.0 6.0 6.0 6.0 2.0 2.0 4.1 1.0 
> 

編輯,因爲我很好奇!

a <- sample(1:10, 1e6, replace=TRUE) 
b <- sample(1:10, 1e6, replace=TRUE) 

> system.time(rep(a, b)) 
    user system elapsed 
    0.140 0.016 0.156 
> system.time(inverse.rle(list(lengths=b, values=a))) 
    user system elapsed 
    0.024 0.004 0.028 
+0

那麼我會被詛咒,我沒有想到! – thelatemail

+0

一個很好的*相對*加速,但不會完全等待整天! – thelatemail

+0

這個加速並沒有發生在我預期的方向!但代表只需要3個字符鍵入;鑑於絕對時間無論如何都是快速的,角色的數量勝過我。因此,接受的解決方案保持。 –

5

只是比rep不同的東西:

> inverse.rle(list(lengths=b,values=a)) 
[1] 1.0 1.0 6.0 6.0 6.0 2.0 2.0 4.1 1.0 
+0

請參閱編輯我的文章。你的'inverse.rle'版本明顯更快! – Justin

+0

@Justin,看到我的帖子 - 它不應該是,它不是。 – mnel

4

一些基準測試和更快的解決方案。 rep.int是在標準使用情況下,更快地實現的rep(從?rep

rep.int(a, b) 

我不相信在基準以上

inverse.rle僅僅是rep.int的包裝。 rep.int應該比rep快。我認爲的inverse.rlewrapper成分應比rep()解釋慢作爲一個原函數

一些microbenchmarking

library(microbenchmark) 

microbenchmark(rep(a,b), rep.int(a,b), 
     inverse.rle(list(values = a, lengths =b))) 
Unit: milliseconds 
             expr  min  lq median  uq 
1 inverse.rle(list(values = a, lengths = b)) 29.06968 29.26267 29.36191 29.67501 
2         rep(a, b) 25.65125 25.76246 25.84869 26.52348 
3        rep.int(a, b) 20.38604 23.31840 23.38940 23.69600 
     max 
1 72.80645 
2 69.00169 
3 66.40759 

沒有太多在裏面,但rep.int出現贏家 - 它應該。

+2

+1 - 好吧,我不會看起來該死的。 – thelatemail

+0

「內部」的代表;不是'整數';哦R的命名約定......非常感謝使用microbenchmark工具的帖子;我肯定今天晚上學到了一些東西。 –