Как удалить временные файлы в параллельной задаче в R

#r #r-raster #parallel-foreach

#r #r-растр #parallel-foreach

Вопрос:

Возможно ли удалить временные файлы из распараллеленной R-задачи?

Я полагаюсь на распараллеливание с помощью doParallel и foreach в R для выполнения различных вычислений на небольших подмножествах огромного растрового файла. Это включает в себя многократное обрезание подмножества большого растра. Мой базовый синтаксис выглядит примерно так:

 grid <- raster::raster("grid.tif")
data <- raster::raster("data.tif")

cl <- parallel::makeCluster(32)
doParallel::registerDoParallel(cl)

m <- foreach(col=ncol(grid)) %:% foreach(row=nrow(grid)) %dopar% {
   
   # get extent of subset 
   cell <- raster::cellFromRowCol(grid, row, col)
   ext <- raster::extentFromCells(grid, cell)
   
   # crop main raster to subset extent
   subset <- raster::crop(data, ext)
   
   # ...
   # perform some processing steps on the raster subset
   # ...
   
   # save results to a separate file
   saveRDS(subset, paste0("output_folder/", row, "_", col)
}
 

Алгоритм работает отлично и достигает того, чего я хочу. Однако raster::crop(data, ext) при каждом вызове создается небольшой временный файл. Это кажется стандартным поведением пакета raster, но это становится проблемой, потому что эти временные файлы удаляются только после выполнения всего кода и занимают слишком много места на диске (сотни ГБ).

При последовательном выполнении задачи я могу просто удалить временный файл с file.remove(subset@file@name) помощью . Однако это больше не работает при параллельном выполнении задачи. Вместо этого команда просто игнорируется, и временный файл остается там, где он есть, пока не будет выполнена вся задача.

Есть идеи относительно того, почему это так и как я мог бы решить эту проблему?

Комментарии:

1. К сожалению, raster пакет плохо работает с большими наборами данных. Несколько лет назад я столкнулся с проблемой, подобной вашей, когда raster записал 2 ТБ временных файлов на диск. Игра с rasterOptions этим не привела к каким-либо значительным улучшениям. Тогда решением было использовать raster аналог Python, который оказался намного более эффективным. Однако теперь у raster пакета есть преемник. Он вызывается terra и работает намного лучше на больших наборах данных. Вы пробовали это использовать?

2. @Chr Нет, я этого не делал, но я посмотрю! Спасибо!

Ответ №1:

Для этого есть функция removeTmpFiles .

Вы должны уметь использовать f <- filename(subset) , избегать чтения из slots ( @ ). Я не понимаю, почему вы не сможете его удалить. Но, возможно, для этого нужно немного повозиться с путем?

временные файлы создаются только тогда, когда пакет raster сочтет это необходимым, исходя из доступной и требуемой оперативной памяти. Смотрите canProcessInMemory( , verbose=TRUE) . Настройки по умолчанию несколько консервативны, и вы можете изменить их с rasterOptions() помощью (memfrac и maxmemory)

Другой подход заключается в предоставлении аргумента filename для обрезки. Тогда вы знаете, что это за имя файла, и можете его удалить. Конечно, вам нужно позаботиться о том, чтобы не перезаписывать данные из разных задач, поэтому вам может потребоваться использовать какой-то уникальный идентификатор, связанный с ним.

saveRDS( ) не будет работать, если растр поддерживается временным файлом (так как он исчезнет).