Как я могу использовать R для поиска искаженных строк и полей в файле, слишком большом для чтения в ОЗУ

У меня есть файл, размер которого превышает общую оперативную память моего компьютера примерно в 10 раз. Я пытаюсь прочитать его в объекте R, который позволит мне просмотреть его и извлечь из него более управляемые фрагменты. Я пробовал разные подходы к этому, но сталкивался с проблемами — разными проблемами — с каждым. У меня есть копия файла в формате фиксированной ширины и еще одна в формате CSV. Я считаю, что файлы в остальном идентичны. Мне удалось прочитать первые 5000 строк и получить предварительную ширину поля для каждого столбца в файле с фиксированной шириной и предварительный класс данных для каждого столбца в обоих файлах. На данный момент я не спрашиваю, как достичь моей общей цели. Вместо этого я хотел бы исключить (или доказать) искажение данных как источник моих ошибок. Если бы я прочитал весь файл, я бы понял, как это сделать. Как есть, не знаю.

Итак, вот мой вопрос: есть ли способ в R читать данные фиксированной ширины или CSV построчно, не читая весь файл в память, и: для CSV проверьте: • если количество полей всегда одинаково, и вернуть номера строк, где это не так; • если данные в каждом поле соответствуют классу столбца, и вернуть номер строки и номер или имя столбца, если это не так.

для фиксированной ширины проверьте: • всегда ли количество символов одинаково, и верните номер строки, если это не так; • соответствуют ли данные в каждом поле классу столбца; и вернуть номер строки и номер первого символа в поле, либо номер столбца, либо имя столбца, если это не так;

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

Как для случаев с фиксированной шириной, так и для CSV проверка классов столбцов должна быть устойчивой к отсутствию или неправильному формату некоторых полей или символов, т. в следующем ряду.

Может быть, есть пакет или функция, которая делает это? Это похоже на довольно стандартную задачу очистки данных, если не считать проблемы с большими файлами.

Любая помощь будет принята с благодарностью.

С уважением, andrewH


person andrewH    schedule 29.09.2013    source источник
comment
не так давно здесь была пара вопросов по той же проблеме. Если вы ищете, вы должны быть в состоянии найти его. Короткий ответ — использовать readLines для чтения файла по частям.   -  person Ricardo Saporta    schedule 29.09.2013


Ответы (1)


Вариант 1. У меня ограниченный опыт работы с данными fwf в «реальных жизненных ситуациях», но для больших CSV-файлов функция count.fields оказалась очень полезной. Попробуй это:

 (table(cnts <- 
      count.fields(paste0(path,filename), sep=",", quote="", comment.char="") )

Затем вы можете искать в cnts номера строк с выбросами. Например, если вы заметили, что было только 10-20 полей из 47, в то время как остальные были 48, вы можете распечатать эти местоположения:

which(cnts=47)

Вариант 2: я почти уверен, что видел решения для этого с использованием sed и grep на системном уровне для подсчета разделителей полей. Я собрал это вместе с некоторых форумов NIX, и это дает мне таблицу количества полей в четырехстрочном файле, который хорошо структурирован:

fct <- table(system("awk -F ',' '{print NF}' A.csv", intern=TRUE))
fct

#3 
#4 

И потребовалось 6 секунд, чтобы подсчитать поля в наборе данных записи 1,2 MM, и ни одно из данных не было перенесено в R:

system.time( fct <- table(system("awk -F ',' '{print NF}' All.csv", intern=TRUE)) )
#   user  system elapsed 
#  6.597   0.215   6.552 

Вы можете получить количество строк с помощью:

sum(fct)
person IRTFM    schedule 29.09.2013