짧은에 운영 할 때 RAM에 너무 큰 될 큰 목록 작업? 어떻게 예를 들어, <code>R</code>에 큰 목록 작업을 디스크에 넣어 다음 섹션에서 작업 할 수 있습니다, 더 많은 RAM을 가진 시스템에서 작업의
다음은 목록에있는 각 데이터 프레임 여기에 빠른 예와는 달리, 고유 내 실제 사용의 경우 내가n = 50; i = 100
WORD <- vector(mode = "integer", length = n)
for (i in 1:n){
WORD[i] <- paste(sample(c(rep(0:9,each=5),LETTERS,letters),5,replace=TRUE),collapse='')
}
dat <- data.frame(WORD = WORD,
COUNTS = sample(1:50, n, replace = TRUE))
dat_list <- lapply(1:i, function(i) dat)
을 사용하고 목록의 유형을 생성하는 일부 코드입니다. 이 몇 시간 동안 실행
FUNC <- function(x) {rep(x$WORD, times = x$COUNTS)}
la <- lapply(dat_list, FUNC)
내 실제 사용 케이스 : 나는이 내가 dataframes이 목록에 수행 할 작업의 한 예입니다 100,000
= 4000와 나는 N을 목표로하고 있습니다 의 RAM을 채우고 스왑의 가장 다음 RStudio는 (RStudio 인해 R 세션에서 오류로 종료하도록 강요했다) 얼고 그 위에 폭탄으로 메시지를 보여줍니다.
나는 bigmemory
이 행렬로 제한되고 ff
은 목록을 처리하지 않는 것으로 보입니다. 다른 옵션은 무엇입니까? 여기에 sqldf
또는 관련 메모리 부족 방법이 가능한 경우 어떻게 시작할 수 있습니까? 어떤 진전을 이루기 위해 문서에서 충분한 정보를 얻을 수 없으며 어떤 조언을해도 감사 할 것입니다. "더 많은 RAM 구매"지침은 무시됩니다. 이것은 평균적인 데스크탑 컴퓨터 (예 : 대학 컴퓨터 실)에 적합 할 것으로 기대되는 패키지를위한 것입니다.
UPDATE SimonO101과 아리의 도움이 의견을 최대 Followining는, 여기에 결과가 여기와와와 GC
# self-contained speed test of untable
n = 50; i = 100
WORD <- vector(mode = "integer", length = n)
for (i in 1:n){
WORD[i] <- paste(sample(c(rep(0:9,each=5),LETTERS,letters),5,replace=TRUE),collapse='')
}
# as data table
library(data.table)
dat_dt <- data.table(WORD = WORD, COUNTS = sample(1:50, n, replace = TRUE))
dat_list_dt <- lapply(1:i, function(i) dat_dt)
# as data frame
dat_df <- data.frame(WORD = WORD, COUNTS = sample(1:50, n, replace = TRUE))
dat_list_df <- lapply(1:i, function(i) dat_df)
# increase object size
y <- 10
dt <- c(rep(dat_list_dt, y))
df <- c(rep(dat_list_df, y))
# untable
untable <- function(x) rep(x$WORD, times = x$COUNTS)
# preallocate objects for loop to fill
df1 <- vector("list", length = length(df))
dt1 <- vector("list", length = length(dt))
df3 <- vector("list", length = length(df))
dt3 <- vector("list", length = length(dt))
# functions for lapply
df_untable_gc <- function(x) { untable(df[[x]]); if (x%%10) invisible(gc()) }
dt_untable_gc <- function(x) { untable(dt[[x]]); if (x%%10) invisible(gc()) }
# speedtests
library(microbenchmark)
microbenchmark(
for(i in 1:length(df)) { df1[[i]] <- untable(df[[i]]); if (i%%10) invisible(gc()) },
for(i in 1:length(dt)) { dt1[[i]] <- untable(dt[[i]]); if (i%%10) invisible(gc()) },
df2 <- lapply(1:length(df), function(i) df_untable_gc(i)),
dt2 <- lapply(1:length(dt), function(i) dt_untable_gc(i)),
for(i in 1:length(df)) { df3[[i]] <- untable(df[[i]])},
for(i in 1:length(dt)) { dt3[[i]] <- untable(dt[[i]])},
df4 <- lapply(1:length(df), function(i) untable(df[[i]])),
dt4 <- lapply(1:length(dt), function(i) untable(dt[[i]])),
times = 10)
없이 dataframes 및 data.tables, 루프와 lapply을 비교 일부 벤치 마크이고, 명시 적 가비지 수집이 없으면 data.table은 루프보다 약간 더 빠르며 느리게 실행됩니다. 명시 적 가비지 콜렉션 (SimonO101이 제안하는 것 같아서)은 모두 동일한 속도입니다. 훨씬 느립니다! 나는 gc
를 사용하여 약간의 논란이 경우 아마 도움이되지 않습니다 것을 알고,하지만 난 그것을 내 실제 사용 사례와 함께 총을 제공하고 어떤 차이가 있는지 확인할 수 있습니다. 물론 필자는 이러한 함수들에 대한 메모리 사용에 관한 어떠한 데이터도 갖고 있지 않다. 이것이 나의 주요 관심사이다. 타이밍 기능과 동일한 메모리 벤치마킹 기능이 없다 (Windows 용).
Unit: milliseconds
expr
for (i in 1:length(df)) { df1[[i]] <- untable(df[[i]]) if (i%%10) invisible(gc()) }
for (i in 1:length(dt)) { dt1[[i]] <- untable(dt[[i]]) if (i%%10) invisible(gc()) }
df2 <- lapply(1:length(df), function(i) df_untable_gc(i))
dt2 <- lapply(1:length(dt), function(i) dt_untable_gc(i))
for (i in 1:length(df)) { df3[[i]] <- untable(df[[i]]) }
for (i in 1:length(dt)) { dt3[[i]] <- untable(dt[[i]]) }
df4 <- lapply(1:length(df), function(i) untable(df[[i]]))
dt4 <- lapply(1:length(dt), function(i) untable(dt[[i]]))
min lq median uq max neval
37436.433962 37955.714144 38663.120340 39142.350799 39651.88118 10
37354.456809 38493.268121 38636.424561 38914.726388 39111.20439 10
36959.630896 37924.878498 38314.428435 38636.894810 39537.31465 10
36917.765453 37735.186358 38106.134494 38563.217919 38751.71627 10
28.200943 29.221901 30.205502 31.616041 34.32218 10
10.230519 10.418947 10.665668 12.194847 14.58611 10
26.058039 27.103217 27.560739 28.189448 30.62751 10
8.835168 8.904956 9.214692 9.485018 12.93788 10
은 당신이 즉, 그것은 사전에 데이터의 여러 사본을하지 않습니다, 그것은 참조로 값을 변경하기 때문에 data.table' 여기에 엄청난 도움이 될 수있는 경우'에서'data.rame' 구조를 사용하는 참조하십시오. 나는 전체 테이블을 개최 RAM에 필요한 공간을 제외하고, 그것을 알고있는 것처럼, 필요한 경우에만 추가 작업 RAM 공간은 긴 목록 요소 (예를 들어,'column')의 길이에 달려있다. 반면에'data.frame'을 사용하면 객체를 작업 할 때 훨씬 더 많은 RAM이 필요합니다. 참조에 의한 변경으로 인해 'data.table'도 * 훨씬 * 빠릅니다. 이 같은'lapply'를 사용하는 경우 –
또한, 나는 그것의 많은 data.frames에 걸쳐 반복, 가비지 컬렉터의 복잡한 너무 잘 모르겠지만, * (그러나 이것은 추측입니다) * 가능 이미 처리 된 데이터에 가비지 콜렉션.* lapply' 루프가 종료 된 후 * 메모리가 가득 찰 때까지 메모리의 프레임이 * 발생할 수 없습니다. 아마도 다른 구조/루핑 메커니즘이 여기에 적합할까요? –
@ SimonO101 나는 동의한다. 나는'luply'를 사용하여 몇 가지 큰 작업을 실패 시켰습니다. 이것은'for' 루프에 간단한 재 작성으로 작업했습니다. –