Сбой после итерации нескольких файлов .lif - PullRequest
0 голосов
/ 24 сентября 2019

Я написал функцию для выполнения:

  • Извлечение изображения из файла .lif в многоканальный стек .tif
  • Расчет максимальной интенсивности z-проекции для каждого канала
  • Создание суммы кадров для размещения поверх стека

Проблема возникает при итерации по нескольким файлам .lif.После первой итерации я получаю сессию сбоя R с RStudio.Если я запускаю эту функцию на терминале, она зависает.

# Increase memory
options( java.parameters = '-Xmx5g' )

# Load needed libraries
library(RBioFormats)
library(EBImage)
library(tidyverse)
library(MaxContrastProjection)

lif_proj = function(contrast){

  # List of Lif files
  lif_ls = list.files('input/lif', pattern = '*.lif', full.names = TRUE)

  # For each LIF file
  lapply(seq(length(lif_ls)), function(x){

    meta = RBioFormats::read.metadata(lif_ls[x])
    no_images = length(meta)

    # For each Image
    lapply(seq(no_images), function(y){

      # ---------- Read Stack Multi-Channel & apply Projection

      no_channels = meta[[y]]$coreMetadata$sizeC

      img = lapply(seq(no_channels), function(z) {
        img = RBioFormats::read.image(lif_ls[x], series = y, subset = list(C = z),
                                      normalize = FALSE,
                                      read.metadata = FALSE,
                                      proprietary.metadata = FALSE) %>%
          MaxContrastProjection::intensityProjection(imageStack = ., projType = 'max') %>%
          EBImage::Image()

        return(img)
      })

      # Output directory Stack
      output_path = 'input/stack/'
      if(!dir.exists(output_path)){dir.create(output_path, recursive = TRUE)}

      filename =  paste0(output_path, 'lif-', sprintf('%02d', x), '_', sprintf('%02d', y), '.tif')

      # Create Merge Frame & Save
      EBImage::writeImage(
          EBImage::combine(EBImage::normalize(Reduce('+', img)) * contrast,
                           EBImage::normalize(EBImage::combine(img))),
          files = filename

      # Clean memory
      img = NULL
      rm(img)
      gc()

    })

    gc()

  })

}

Как вы можете видеть:

  • Чтобы предотвратить нехватку памяти, перед загрузкой библиотеки RBioFormats яувеличение доступной памяти (некоторые файлы .lif занимают около 3 ГБ, а результирующие изображения - около 200 МБ)
  • Чтобы предотвратить накопление большого объекта img, преобразуйте объект img в NULL (в некоторых сообщениях, которые я мог видетьэто быстрее, чем удалить), чтобы облегчить среду, удалить img объект и сборщик мусора с gc() (на каждой итерации lapply и nested-lapply)
  • Использование normalize = FALSE и read.metadata = FALSE и'propietary.metadata = FALSE на RBioFormats::read.image, чтобы предотвратить большой img размер.Мне нужна нормализованная версия, поэтому она применяется на последнем шаге
  • Запись стека изображений напрямую без назначения в качестве объекта, чтобы предотвратить нехватку памяти

Кажется, что вторая итерациязапускается, но, возможно, вылетает при записи файла на диск.Я пытался заменить EBImage::writeImage на RBioFormats::write.image функцию, но я получаю ту же ошибку.Я попытался разделить эту функцию на выделенную для выполнения максимальной проекции и создания одного стека изображений, чтобы вызвать его во вложенную область, избегая существования большого объекта img в первой области, но она не работает.

Я проверил, есть ли какой-нибудь битый файл .lif или что-то в этом роде, но это нормально.Если я вручную присваиваю переменную x и запускаю только вложенный пакет lapply, он работает, поэтому ошибка заключается в способе выполнения итерации между файлами .lif.

Наконец, я попытался использовать mclapply для первого lapply, для пакета parallel, но функция не запускается.В идеале было бы желательно применить распараллеливание для вложенных lapply, но я пробовал несколько сценариев и никогда не работал.

Любая помощь?спасибо

...