ошибка read.table(), хотя все элементы присутствуют

Я получаю сообщение об ошибке с read.table():

data <- read.table(file, header=T, stringsAsFactors=F, sep="@")
Error in scan(file, what, nmax, sep, dec, quote, skip, nlines, na.strings,  : 
  line 160 did not have 28 elements

Я проверил строку 160, и в ней было 28 элементов (в ней было 27 символов @).

Я проверил все 30242 строки, там было 816534 символа @, то есть 27 на строку, поэтому я почти уверен, что в каждой строке 28 элементов. Я также проверил файл, чтобы убедиться, что в нем нет никаких символов @, кроме как в качестве разделителей.

Кто-нибудь имеет представление о том, что здесь происходит?

изменить: строка 160 файла

158@Mental state: 1. Overall clinical symptoms@MD@S@2002@CMP-005@[email protected]@23.58@Clozapine versus typical neuroleptic medication for schizophrenia@[email protected]@02@SENSITIVITY ANALYSIS - CHINESE TRIALS@[email protected]@Fixed@16@5@2@45@Chinese trials@YES@Xia 2002 (CPZ)@STD-Xia-2002-_x0028_CPZ_x0029_@579@566@40

edit2: строка 161 файла

159@Length of surgery (minutes)@MD@Y@1995@CMP-001@[email protected]@47.0@Gamma and other cephalocondylic intramedullary nails versus extramedullary implants for extracapsular hip fractures in adults@[email protected]@01@Summary: Femoral nail (all types) versus sliding hip screw (SHS)@[email protected]@Random@12@1@1@53@Gamma nail@YES@O'Brien 1995@STD-O_x0027_Brien-1995@958@941@49

person user3821273    schedule 21.02.2015    source источник
comment
Попробуйте прочитать разделы ваших данных вокруг проблемной строки, используя аргументы skip и nrows, чтобы увидеть, сможете ли вы изолировать проблему.   -  person user20650    schedule 21.02.2015
comment
По какой-то причине, когда я использовал read.csv с аргументом sep=@, он работал нормально.   -  person user3821273    schedule 21.02.2015
comment
Хм... возможно, вам нужно было установить fill=TRUE в read.table . (хотя это предполагает проблему, которую учитывает fill, на которую следует обратить внимание)   -  person user20650    schedule 21.02.2015
comment
Как выглядит строка №160?   -  person lukeA    schedule 21.02.2015
comment
Покажите нам уже строку 160. Там может быть какой-то пропуск.   -  person smci    schedule 21.02.2015
comment
Попробуйте использовать некоторые другие аргументы, такие как strip.white, flush и т. д. Значения по умолчанию для read.csv и read.table не совпадают.   -  person Rich Scriven    schedule 21.02.2015
comment
Если в строке есть символ решетки (#), read.table будет рассматривать его как комментарий (игнорируя его и все после него), в то время как read.csv по умолчанию имеет значение comment.char=, что не будет вести себя таким образом. , так что это может быть причиной.   -  person ping    schedule 21.02.2015
comment
@ user2060, CSV — это термин с нечетким определением, означающий текстовый формат с постоянной шириной столбцов; read.csv() в R — это не что иное, как read.table(...,header = TRUE, sep = ",", quote = "\"") - это тот же код. Независимо от того, какой у вас символ-разделитель, основная проблема будет одна и та же. Пользователи read.csv() могут извлечь пользу из вашего опыта.   -  person smci    schedule 21.02.2015
comment
Ну, на самом деле это означает значения, разделенные запятыми   -  person Rich Scriven    schedule 21.02.2015
comment
Кроме того, я думаю, что, поскольку у вас есть заголовок = TRUE, проблема на самом деле в строке 161 файла.   -  person ping    schedule 21.02.2015
comment
Может быть, это ' в O'Brien, который вы могли бы обойти с помощью quote=, если это не сломает что-то еще; но в моем тесте выдавалось другое сообщение об ошибке (неполная последняя строка, найденная readTableHeader)   -  person ping    schedule 21.02.2015
comment
read.table(file, header=T, sep="@", comment.char="", quote="\"") похоже решил проблему.   -  person user3821273    schedule 21.02.2015


Ответы (2)


Я думаю, проблема в том, что есть символ новой строки, который должен быть распознан аргументом quote. Давайте посмотрим.

txt <- c(
    "158@Mental state: 1. Overall clinical symptoms@MD@S@2002@CMP-005@[email protected]@23.58@Clozapine versus typical neuroleptic medication for schizophrenia@[email protected]@02@SENSITIVITY ANALYSIS - CHINESE TRIALS@[email protected]@Fixed@16@5@2@45@Chinese trials@YES@Xia 2002 (CPZ)@STD-Xia-2002-_x0028_CPZ_x0029_@579@566@40", 
    "159@Length of surgery (minutes)@MD@Y@1995@CMP-001@[email protected]@47.0@Gamma and other cephalocondylic intramedullary nails versus extramedullary implants for extracapsular hip fractures in adults@[email protected]@01@Summary: Femoral nail (all types) versus sliding hip screw (SHS)@[email protected]@Random@12@1@1@53@Gamma nail@YES@O'Brien 1995@STD-O_x0027_Brien-1995@958@941@49"
)

Мы можем использовать count.fields() для предварительного просмотра длин полей в файле. С обычным sep = "@" и ничем другим мы получаем NA между строками и неправильные подсчеты.

count.fields(textConnection(txt), sep = "@")
# [1] 28 NA 24

Но когда мы распознаем разделитель новой строки в quote, он возвращает правильную длину.

count.fields(textConnection(txt), sep = "@", quote = "\n")
# [1] 28 28 

Итак, я рекомендую вам добавить quote = "\n" к вашему вызову read.table и посмотреть, решит ли это проблему. Это сделало для меня

read.table(text = txt, sep = "@")
# [1] V1  V2  V3  V4  V5  V6  V7  V8  V9  V10 V11 V12 V13 V14 V15 V16 V17 V18 V19 V20 V21 V22 V23 V24 V25 V26 V27 V28
# <0 rows> (or 0-length row.names)

df <- read.table(text = txt, sep = "@", quote = "\n")
dim(df)
# [1]  2 28
anyNA(df)
# [1] FALSE
person Rich Scriven    schedule 21.02.2015
comment
Спасибо, это было проблемой. - person user3821273; 21.02.2015
comment
Я не уверен, почему. У меня есть подозрение, что некоторые из этих подстрок выглядят как шестнадцатеричные символы Юникода, но я не уверен. - person Rich Scriven; 21.02.2015

У меня была такая же проблема. Этот ответ помог, но quote="\n" работал только до определенного момента. В файле был элемент, который имел " в качестве символа, поэтому мне пришлось использовать значение по умолчанию для кавычки. У меня также был # в одном из элементов, поэтому мне пришлось использовать comment.char="". В справке для read.table() упоминается scan() в паре мест, поэтому я проверил его и обнаружил, что аргумент allowEscapes имеет False по умолчанию. Я добавил его в свой read.table() и установите для него значение True. Вот полная команда, которая сработала для меня: read.table(file="filename.csv", header=T, sep=" ,", comment.char="", allowEscapes=T) Надеюсь, это кому-нибудь поможет.

person W. Crawford    schedule 26.10.2016
comment
Это помогло мне кучу,. comment.char= это путь. - person Maxwell Chandler; 27.01.2017