2013-04-02 34 views
7

Tôi đọc trong một file dữ liệu mà trông như thế này:Kỹ thuật cho việc tìm kiếm dữ liệu xấu trong read.csv trong R

userId, fullName,email,password,activated,registrationDate,locale,notifyOnUpdates,lastSyncTime,plan_id,plan_period_months,plan_price,plan_exp_date,plan_is_trial,plan_is_trial_used,q_hear,q_occupation,pp_subid,pp_payments,pp_since,pp_cancelled,apikey 
"2","John Smith,"[email protected]","a","1","2004-07-23 14:19:32","en_US","1","2011-04-07 07:29:17","3",\N,\N,\N,"0","1",\N,\N,\N,\N,\N,\N,"d7734dce-4ae2-102a-8951-0040ca38ff83" 

nhưng các tập tin thực tế như khoảng 20000 hồ sơ. Tôi sử dụng mã R sau đây để đọc nó trong:

user = read.csv("~/Desktop/dbdump/users.txt", na.strings = "\\N", quote="") 

Và lý do tôi có quote="" là vì không có nó nhập sớm. Tôi kết thúc với tổng số 9569 quan sát. Tại sao tôi không hiểu tại sao chính xác quote="" khắc phục được sự cố này, nó dường như là để làm như vậy.

Ngoại trừ việc nó giới thiệu các vấn đề khác mà tôi phải 'khắc phục'. Người đầu tiên tôi thấy là ngày kết thúc là chuỗi bao gồm các dấu ngoặc kép, mà không muốn chuyển đổi sang ngày thực tế khi tôi sử dụng to.Date() trên chúng.

Bây giờ tôi có thể sửa các chuỗi và hack theo cách của mình. Nhưng tốt hơn để biết thêm về những gì tôi đang làm. Ai đó có thể giải thích:

  1. Tại sao quote="" sửa chữa 'dữ liệu xấu'
  2. một kỹ thuật thực hành tốt nhất để tìm ra những gì đang gây ra read.csv để ngăn chặn sớm là gì? (Nếu tôi chỉ nhìn vào dữ liệu đầu vào tại +/- hàng được chỉ định, tôi không thấy bất kỳ điều gì không ổn).

Dưới đây là các dòng 'gần' vấn đề ''. Tôi không thấy những thiệt hại làm bạn?

"16888","user1","[email protected]","TeilS12","1","2008-01-19 08:47:45","en_US","0","2008-02-23 16:51:53","1",\N,\N,\N,"0","0","article","student",\N,\N,\N,\N,"ad949a8e-17ed-102b-9237-0040ca390025" 
"16889","user2","[email protected]","Gaspar","1","2008-01-19 10:34:11","en_US","1",\N,"1",\N,\N,\N,"0","0","email","journalist",\N,\N,\N,\N,"8b90f63a-17fc-102b-9237-0040ca390025" 
"16890","user3","[email protected]","boomblaadje","1","2008-01-19 14:36:54","en_US","0",\N,"1",\N,\N,\N,"0","0","article","student",\N,\N,\N,\N,"73f31f4a-181e-102b-9237-0040ca390025" 
"16891","user4","[email protected]","mytyty","1","2008-01-19 15:10:45","en_US","1","2008-01-19 15:16:45","1",\N,\N,\N,"0","0","google-ad","student",\N,\N,\N,\N,"2e48e308-1823-102b-9237-0040ca390025" 
"16892","user5","[email protected]","08091969","1","2008-01-19 15:12:50","en_US","1",\N,"1",\N,\N,\N,"0","0","dont","dont",\N,\N,\N,\N,"79051bc8-1823-102b-9237-0040ca390025" 

* Cập nhật *

Đó là khó khăn hơn. Mặc dù tổng số hàng được nhập là 9569, nếu tôi xem xét một vài hàng cuối cùng, chúng tương ứng với một vài dòng dữ liệu cuối cùng. Vì vậy, tôi phỏng đoán rằng có điều gì đó đã xảy ra trong quá trình nhập để gây ra nhiều hàng bị bỏ qua. Trên thực tế, 15914 - 9569 = 6345 bản ghi. Khi tôi có báo giá = "" ở đó, tôi nhận được 15914.

Vì vậy, câu hỏi của tôi có thể được sửa đổi: Có cách nào để đọc read.csv báo cáo về các hàng mà nó quyết định không nhập không?

* CẬP NHẬT 2 *

@Dwin, tôi đã phải gỡ bỏ na.strings = "\ N" vì count.fields chức năng không cho phép nó. Với điều đó, tôi nhận được kết quả này trông thú vị nhưng tôi không hiểu nó.

3  4 22 23 24 
1 83 15466 178  4 

lệnh thứ hai của bạn tạo ra một rất nhiều dữ liệu (và dừng lại khi max.print là đạt.) Nhưng hàng đầu tiên là thế này:

[1] 2 4 2 3 5 3 3 3 5 3 3 3 2 3 4 2 3 2 2 3 2 2 4 2 4 3 5 4 3 4 3 3 3 3 3 2 4 

Mà tôi không hiểu nếu đầu ra là cho thấy có bao nhiêu trường trong mỗi bản ghi đầu vào. Rõ ràng là những dòng đầu tiên đều có hơn 2,4,2 lĩnh vực vv ... Cảm thấy như tôi đang tiến gần hơn, nhưng vẫn còn bối rối!

+2

Bạn có thể cho chúng tôi biết dữ liệu trông như thế nào trước 'quote =" "' và sau? Hoặc, bạn có thể đăng thêm một vài dòng dữ liệu của mình hay không, tốt nhất là một số dòng "lành mạnh" và một số dữ liệu xấu? Tóm lại, bạn có thể tạo một ví dụ tái sản xuất được không? –

+0

Tôi bỏ phiếu cho các dấu phẩy được nhúng! – Justin

+0

@roman: vấn đề là tôi không biết dữ liệu xấu ở đâu. Tôi có thể chỉ cho bạn các dòng +/- 9569 và có thể bạn sẽ thấy những gì tôi đang thiếu. – pitosalas

Trả lời

4

Một vấn đề tôi đã phát hiện (nhờ data.table) là báo giá còn thiếu (") sau John Smith. Đây có phải là vấn đề đối với các dòng khác không?

Nếu tôi thêm trích dẫn "bị thiếu" sau John Smith, nó sẽ ổn.

tôi lưu dữ liệu này để data.txt:

userId, fullName,email,password,activated,registrationDate,locale,notifyOnUpdates,lastSyncTime,plan_id,plan_period_months,plan_price,plan_exp_date,plan_is_trial,plan_is_trial_used,q_hear,q_occupation,pp_subid,pp_payments,pp_since,pp_cancelled,apikey 
"2","John Smith","[email protected]","a","1","2004-07-23 14:19:32","en_US","1","2011-04-07 07:29:17","3",\N,\N,\N,"0","1",\N,\N,\N,\N,\N,\N,"d7734dce-4ae2-102a-8951-0040ca38ff83" 
"16888","user1","[email protected]","TeilS12","1","2008-01-19 08:47:45","en_US","0","2008-02-23 16:51:53","1",\N,\N,\N,"0","0","article","student",\N,\N,\N,\N,"ad949a8e-17ed-102b-9237-0040ca390025" 
"16889","user2","[email protected]","Gaspar","1","2008-01-19 10:34:11","en_US","1",\N,"1",\N,\N,\N,"0","0","email","journalist",\N,\N,\N,\N,"8b90f63a-17fc-102b-9237-0040ca390025" 
"16890","user3","[email protected]","boomblaadje","1","2008-01-19 14:36:54","en_US","0",\N,"1",\N,\N,\N,"0","0","article","student",\N,\N,\N,\N,"73f31f4a-181e-102b-9237-0040ca390025" 
"16891","user4","[email protected]","mytyty","1","2008-01-19 15:10:45","en_US","1","2008-01-19 15:16:45","1",\N,\N,\N,"0","0","google-ad","student",\N,\N,\N,\N,"2e48e308-1823-102b-9237-0040ca390025" 
"16892","user5","[email protected]","08091969","1","2008-01-19 15:12:50","en_US","1",\N,"1",\N,\N,\N,"0","0","dont","dont",\N,\N,\N,\N,"79051bc8-1823-102b-9237-0040ca390025" 

Và đây là một mã. Cả hai freadread.csv đều hoạt động tốt.

require(data.table) 

dat1 <- fread("data.txt", header = T, na.strings = "\\N") 
dat1 

dat2 <- read.csv("data.txt", header = T, na.strings = "\\N") 
dat2 
4

Chức năng count.fields có thể rất hữu ích trong việc xác định nơi cần tìm dữ liệu không đúng định dạng.

này đưa ra một bảng về trường trên mỗi dòng bỏ qua trích dẫn, có thể là một vấn đề nếu có được nhúng dấu phẩy:

table(count.fields("~/Desktop/dbdump/users.txt", quote="", sep=",")) 

này đưa ra một lập bảng bỏ qua cả hai dấu ngoặc kép và "#" (octothorpe) như là một nhân vật bình luận:

table(count.fields("~/Desktop/dbdump/users.txt", quote="", comment.char="")) 

Atfer nhìn thấy những gì bạn báo cáo cho lập bảng đầu tiên ..... hầu hết trong số đó là như mong muốn ... bạn có thể có được một danh sách các vị trí phù hợp với phi 22 giá trị (bằng cách sử dụng dấu phẩy và phi cài đặt -quote):

which(count.fields("~/Desktop/dbdump/users.txt", quote="", sep=",") != 22) 

Đôi khi vấn đề có thể được giải quyết với fill=TRUE nếu khó khăn duy nhất thiếu dấu phẩy ở cuối dòng.

+0

Đây là phiên bản tốt hơn cho đề xuất của tôi. +1 –

Các vấn đề liên quan