Làm sạch và chuẩn bị dữ liệu bằng Python cho khoa học dữ liệu - Thực tiễn tốt nhất và các gói hữu ích

Lời nói đầu

Làm sạch dữ liệu chỉ là một cái gì đó mà bạn sẽ phải đối phó trong phân tích. Nó không phải là công việc tuyệt vời, nhưng nó phải được thực hiện để bạn có thể tạo ra công việc tuyệt vời.

Tôi đã dành rất nhiều thời gian để viết và viết lại các chức năng để giúp tôi dọn dẹp dữ liệu, đến mức tôi muốn chia sẻ một số điều tôi đã học được trên đường đi. Nếu bạn chưa xem qua bài đăng này, về cách tổ chức tốt hơn các dự án khoa học dữ liệu, hãy kiểm tra nó vì nó sẽ giúp hình thành một số khái niệm mà tôi sẽ trình bày dưới đây.

Sau khi bắt đầu tổ chức mã của mình tốt hơn, tôi đã bắt đầu giữ một gói tùy chỉnh trong đó tôi giữ dọn sạch mã của mình. Nếu có bất cứ điều gì khác, nó cung cấp cho tôi một đường cơ sở để viết các phương thức tùy chỉnh trên dữ liệu không hoàn toàn phù hợp với các tập lệnh dọn sạch trước đây của tôi. Và, tôi không cần phải viết trình trích xuất email regex đó lần thứ 100 vì tôi đã lưu nó ở một vị trí có thể truy cập được.

Một số công ty có toàn bộ đội ngũ chuyên làm sạch mã, nhưng hầu hết don don. Vì vậy, nó tốt nhất để hiểu một số thực hành tốt nhất. Nếu có bất cứ điều gì, bạn sẽ hiểu rõ hơn về cấu trúc dữ liệu của mình, vì vậy để giải thích rõ hơn tại sao hoặc tại sao không có điều gì đó xảy ra.

Ngoài ra, khi chuẩn bị cho bài đăng này, tôi đã chạy qua repo này bởi kjam, điều này sẽ vô cùng hữu ích khi tôi lần đầu tiên học cách làm sạch dữ liệu. Nếu bạn muốn đi sâu hơn vào việc làm sạch mã, tôi khuyên bạn nên bắt đầu từ đó.

Mục tiêu của bạn là dọn dẹp mọi thứ hoặc ít nhất là cố gắng

Kiểm tra dữ liệu của bạn một cách nhanh chóng

Điều đầu tiên bạn muốn làm khi nhận được một tập dữ liệu mới, là nhanh chóng xác minh nội dung bằng phương thức .head ().

gấu trúc nhập khẩu như pd
df = pd.read_csv ('path_to_data')
df.head (10)
>>
... một số đầu ra ở đây ...

Bây giờ, hãy nhanh chóng nhìn thấy tên và loại cột. Hầu hết thời gian bạn sẽ nhận được dữ liệu không hoàn toàn như bạn mong đợi, chẳng hạn như ngày thực sự là chuỗi và các số lẻ khác. Nhưng để kiểm tra trả trước.

# Nhận tên cột
cột_names = df.columns
in (cột_names)
# Nhận các kiểu dữ liệu cột
df.dtypes
# Ngoài ra kiểm tra xem cột là duy nhất
cho tôi trong cột_names:
  print ('{} là duy nhất: {}'. định dạng (i, df [i] .is_unique))

Bây giờ, hãy xem, nếu khung dữ liệu có một chỉ mục được liên kết với nó, bằng cách gọi .index trên df. Nếu không có chỉ mục, bạn sẽ nhận được một AttributionError: ‘hàm đối tượng Hàm không có thuộc tính‘ chỉ số lỗi lỗi được hiển thị.

# Kiểm tra các giá trị chỉ mục
df.index.values
# Kiểm tra nếu một chỉ mục nhất định tồn tại
'foo' trong df.index.values
# Nếu chỉ mục không tồn tại
df.set_index ('cột_name_to_use', inplace = True)

Tốt Dữ liệu của chúng tôi đã được kiểm tra nhanh chóng, chúng tôi biết các loại dữ liệu, nếu các cột là duy nhất và chúng tôi biết nó có một chỉ mục để chúng tôi có thể tham gia và hợp nhất sau này. Hãy để ý xem những cột nào bạn muốn giữ hoặc xóa. Trong ví dụ này, chúng tôi muốn loại bỏ các cột trong các chỉ mục 1, 3 và 5, vì vậy tôi đã chỉ thêm các giá trị chuỗi vào danh sách, sẽ được sử dụng để thả các cột.

# Tạo danh sách hiểu các cột bạn muốn mất
Cột_to_drop = [cột_names [i] cho i trong [1, 3, 5]]
# Thả các cột không mong muốn
df.drop (Cột_to_drop, inplace = True, trục = 1)

Inplace = True đã được thêm vào nên bạn không cần lưu trên df ban đầu bằng cách gán kết quả của .drop () cho df. Nhiều phương pháp trong gấu trúc hỗ trợ inplace = True, vì vậy hãy cố gắng sử dụng nó càng nhiều càng tốt để tránh việc gán lại không cần thiết.

Phải làm gì với NaN

Nếu bạn cần điền vào các lỗi hoặc khoảng trống, hãy sử dụng các phương thức fillna () và dropna (). Có vẻ nhanh chóng, nhưng tất cả các thao tác dữ liệu nên được ghi lại để bạn có thể giải thích chúng cho ai đó sau.

Bạn có thể điền vào NaN bằng các chuỗi hoặc nếu chúng là số bạn có thể sử dụng giá trị trung bình hoặc giá trị trung bình. Có rất nhiều tranh luận về những gì làm với dữ liệu bị thiếu hoặc không đúng định dạng, và câu trả lời chính xác là tùy thuộc vào nó.

Bạn phải sử dụng phán đoán và đầu vào tốt nhất từ ​​những người bạn làm việc với lý do tại sao xóa hoặc điền dữ liệu là cách tiếp cận tốt nhất.

# Điền NaN bằng ''
df ['col'] = df ['col']. fillna ('')
# Điền NaN với 99
df ['col'] = df ['col']. fillna (99)
# Điền NaN với giá trị trung bình của cột
df ['col'] = df ['col']. fillna (df ['col']. mean ())

Bạn cũng có thể truyền bá các giá trị không null về phía trước hoặc phía sau bằng cách đặt phương thức = ở chế độ pad, làm đối số phương thức. Nó sẽ điền giá trị tiếp theo vào khung dữ liệu bằng giá trị không NaN trước đó. Có thể bạn chỉ muốn điền một giá trị (giới hạn = 1) hoặc bạn muốn điền tất cả các giá trị. Dù nó là gì, hãy chắc chắn rằng nó phù hợp với phần còn lại của việc làm sạch dữ liệu của bạn.

df = pd.DataFrame (data = {'col1': [np.nan, np.nan, 2,3,4, np.nan, np.nan]})
    col1
0 NaN
1 NaN
2 2.0
3 3.0
4 4.0 # Đây là giá trị để điền vào
5 NaN
6 NaN
df.fillna (phương thức = 'pad', giới hạn = 1)
    col1
0 NaN
1 NaN
2 2.0
3 3.0
4 4.0
5 4.0 # Hoàn thành chuyển tiếp
6 NaN

Lưu ý làm thế nào chỉ có chỉ số 5 được điền? Nếu tôi không điền vào giới hạn pad, nó sẽ lấp đầy toàn bộ khung dữ liệu. Chúng tôi không giới hạn để điền vào phía trước, mà còn lấp đầy bằng bfill.

# Điền hai giá trị NaN đầu tiên bằng giá trị khả dụng đầu tiên
df.fillna (phương thức = 'bfill')
    col1
0 2.0 # Đã điền
1 2.0 # Đã điền
2 2.0
3 3.0
4 4.0
5 NaN
6 NaN

Bạn chỉ có thể thả chúng từ khung dữ liệu hoàn toàn, theo hàng hoặc theo cột.

# Thả bất kỳ hàng nào có bất kỳ nans nào
df.dropna ()
# Thả cột có bất kỳ nans nào
df.dropna (trục = 1)
# Chỉ thả các cột có ít nhất 90% không phải NaN
df.dropna (thresh = int (df.shape [0] * .9), trục = 1)

Tham số thresh = N yêu cầu một cột có ít nhất N không phải NaN để tồn tại. Hãy nghĩ về điều này như giới hạn thấp hơn cho dữ liệu bị thiếu mà bạn sẽ thấy chấp nhận được trong các cột của mình. Xem xét một số dữ liệu đăng nhập có thể bỏ lỡ một số bộ sưu tập các tính năng. Bạn chỉ muốn các bản ghi có 90% các tính năng khả dụng trước khi bạn coi chúng là ứng cử viên cho mô hình của mình.

np.where (if_this_is_true, do_this, other_do_that)

Tôi có lỗi khi không sử dụng điều này sớm hơn trong sự nghiệp phân tích của mình vì nó vượt quá hữu ích. Nó tiết kiệm rất nhiều thời gian và sự thất vọng khi đi qua một khung dữ liệu. Nếu bạn muốn thực hiện một số thao tác làm sạch cơ bản hoặc tính năng kỹ thuật nhanh chóng, np.where ở đây là cách bạn có thể làm điều đó.

Xem xét nếu bạn đánh giá một cột và bạn muốn biết liệu các giá trị có lớn hơn 10. Nếu chúng là bạn muốn kết quả là 'foo' và nếu không bạn muốn kết quả là 'bar'.

# Thực hiện theo cú pháp này
np.where (if_this_condition_is_true, do_this, other_this)
# Thí dụ
df ['new_column'] = np.where (df [i]> 10, 'foo', 'bar)

Bạn có thể thực hiện các thao tác phức tạp hơn như hoạt động dưới đây. Ở đây chúng tôi đang kiểm tra nếu bản ghi cột bắt đầu bằng foo và không kết thúc bằng thanh. Nếu kiểm tra này, chúng tôi sẽ trả về Đúng, chúng tôi sẽ trả về giá trị hiện tại trong cột.

df ['new_column'] = np.where (df ['col']. str.startswith ('foo') và
                            không phải df ['col']. str.endswith ('bar'),
                            Thật,
                            df ['col'])

Và thậm chí hiệu quả hơn, bạn có thể bắt đầu lồng np của mình vào mọi nơi để chúng xếp chồng lên nhau. Tương tự như cách bạn sắp xếp các hoạt động ternary, hãy chắc chắn rằng chúng có thể đọc được vì bạn có thể nhanh chóng gặp rắc rối với các câu lệnh được lồng rất nhiều.

# Ba cấp độ lồng với np.where
np.where (if_this_condition_is_true_one, do_this,
  np.where (if_this_condition_is_true_two, do_that,
    np.where (if_this_condition_is_true_three, do_foo, do_bar)))
# Một ví dụ tầm thường
df ['foo'] = np.where (df ['bar'] == 0, 'Không',
              np.where (df ['bar'] == 1, 'Một',
                np.where (df ['bar'] == 2, 'Hai', 'Ba')))

Khẳng định và kiểm tra những gì bạn có

Tín dụng vào https://www.programiz.com

Chỉ vì bạn có dữ liệu của mình trong một khung dữ liệu đẹp, không trùng lặp, không thiếu giá trị, bạn vẫn có thể gặp một số vấn đề với dữ liệu cơ bản. Và, với khung dữ liệu gồm 10 triệu + hàng hoặc API mới, làm thế nào bạn có thể đảm bảo các giá trị chính xác như những gì bạn mong đợi?

Sự thật là, bạn không bao giờ thực sự biết liệu dữ liệu của mình có đúng hay không cho đến khi bạn kiểm tra nó. Thực tiễn tốt nhất trong công nghệ phần mềm phụ thuộc rất nhiều vào việc kiểm tra công việc của họ, nhưng đối với khoa học dữ liệu thì đó vẫn là một công việc đang tiến triển. Tốt hơn là bắt đầu ngay bây giờ và dạy cho mình những nguyên tắc làm việc tốt, thay vì phải kiềm chế bản thân vào một ngày sau đó.

Hãy để hệ thống dữ liệu đơn giản để kiểm tra.

df = pd.DataFrame (data = {'col1': np.random.randint (0, 10, 10), 'col2': np.random.randint (-10, 10, 10)})
>>
   col1 col2
0 0 6
1 6 -1
2 8 4
3 0 5
4 3 -7
5 4 -5
6 3 -10
7 9-8
8 0 4
9 7 -4

Hãy thử nghiệm nếu tất cả các giá trị trong col1> = 0 bằng cách sử dụng xác nhận phương thức tích hợp đi kèm với thư viện chuẩn trong python. Những gì bạn có thể hỏi python nếu là True tất cả các mục trong df [‘col1 '] đều lớn hơn 0. Nếu đây là True thì tiếp tục theo cách của bạn, nếu không ném lỗi.

khẳng định (df ['col1']> = 0) .all () # Không nên trả về

Tuyệt vời dường như đã làm việc. Nhưng nếu .all () không được bao gồm trong khẳng định thì sao?

khẳng định (df ['col1']> = 0)
>>
ValueError: Giá trị thật của Sê-ri là mơ hồ. Sử dụng a.empty, a.bool (), a.item (), a.any () hoặc a.all ().

Humm có vẻ như chúng tôi có một số tùy chọn khi chúng tôi thử nghiệm các tệp dữ liệu của chúng tôi. Hãy để thử nghiệm trên đường là bất kỳ giá trị nào là chuỗi.

khẳng định (df ['col1']! = str) .any () # Không nên trả về

Còn về việc kiểm tra hai cột để xem chúng có bằng nhau không?

khẳng định (df ['col1'] == df ['col2']). all ()
>>
TracBack (cuộc gọi gần đây nhất vừa qua):
  Tệp "", dòng 1, trong 
Khẳng địnhError

Ah, khẳng định của chúng tôi đã thất bại ở đây!

Cách thực hành tốt nhất với các xác nhận là được sử dụng để kiểm tra các điều kiện trong dữ liệu của bạn không bao giờ xảy ra. Điều này là như vậy khi bạn chạy mã của mình, mọi thứ dừng lại nếu một trong những xác nhận này thất bại.

Phương thức .all () sẽ kiểm tra xem tất cả các phần tử trong các đối tượng có vượt qua khẳng định hay không, trong khi .any () sẽ kiểm tra xem có bất kỳ phần tử nào trong các đối tượng vượt qua kiểm tra xác nhận hay không.

Điều này có thể hữu ích khi bạn muốn:

  • Kiểm tra nếu có bất kỳ giá trị âm đã được đưa vào dữ liệu;
  • Đảm bảo hai cột giống hệt nhau;
  • Xác định kết quả của một phép biến đổi, hoặc;
  • Kiểm tra xem số id duy nhất có chính xác không.

Có nhiều phương pháp khẳng định hơn mà tôi đã thắng, nhưng hãy làm quen với những phương pháp mà bạn có thể sử dụng ở đây. Bạn không bao giờ biết khi nào bạn cần kiểm tra một điều kiện nhất định, đồng thời, bạn cần bắt đầu thử nghiệm các điều kiện mà bạn không muốn trong mã của mình.

Don thử nghiệm mọi thứ, nhưng kiểm tra những thứ sẽ phá vỡ mô hình của bạn.

Ví dụ. Là một tính năng nên có tất cả là 0 và 1, thực sự được điền với các giá trị đó.

Ngoài ra, gấu trúc gói kỳ diệu đó cũng bao gồm một gói thử nghiệm.

nhập pandas.util.testing như tm
tm.assert_series_equal (df ['col1'], df ['col2'])
>>
AssertsError: Series khác nhau
Giá trị sê-ri khác nhau (100,0%)
[trái]: [0, 6, 8, 0, 3, 4, 3, 9, 0, 7]
[phải]: [6, -1, 4, 5, -7, -5, -10, -8, 4, -4]

Không chỉ chúng tôi nhận được một lỗi ném, mà gấu trúc còn cho chúng tôi biết những gì đã sai.

Đẹp.

Ngoài ra, nếu bạn muốn bắt đầu xây dựng cho mình một bộ thử nghiệm - và bạn có thể muốn nghĩ về việc này - hãy làm quen với gói không đáng tin cậy nhất được tích hợp trong thư viện Python. Bạn có thể tìm hiểu thêm về điều đó ở đây.

làm đẹp

Thay vì phải viết regex của riêng bạn - đó là một nỗi đau vào thời điểm tốt nhất - đôi khi nó đã được thực hiện cho bạn. Gói làm đẹp có thể giúp bạn dọn dẹp một số mẫu thường được sử dụng cho email hoặc URL. Nó không có gì lạ mắt nhưng có thể nhanh chóng giúp dọn dẹp.

$ Pip3 cài đặt làm đẹp
từ Email nhập làm đẹp, Url
email_opes = 'foo@bar.com'
email = Email (email_ chuỗi)
in (email.domain)
in (email.username)
in (email.is_free_email)
>>
thanh.com
foo
Sai trái
url_opes = 'https://github.com/labtocat/beautifier/blob/master/beautifier/__init__.py'
url = Url (url_ chuỗi)
in (url.param)
in (url.username)
in (url.domain)
>>
không ai
Tính năng {'dir': 'hiện chỉ khả dụng với các url được liên kết'}
github.com

Tôi sử dụng gói này khi tôi có hàng loạt URL tôi cần để xử lý và không muốn viết regex lần thứ 100 để trích xuất một số phần của địa chỉ.

Xử lý Unicode

Khi thực hiện một số NLP, việc xử lý Unicode có thể gây khó chịu vào thời điểm tốt nhất. Tôi sẽ chạy một cái gì đó trong spaCy và đột nhiên mọi thứ sẽ phá vỡ tôi vì một số ký tự unicode xuất hiện ở đâu đó trong thân tài liệu.

Nó thực sự là tồi tệ nhất.

Bằng cách sử dụng ftfy (đã sửa lỗi cho bạn), bạn có thể sửa lỗi Unicode thực sự bị hỏng. Hãy xem xét khi ai đó đã mã hóa Unicode với một tiêu chuẩn và giải mã nó bằng một tiêu chuẩn khác. Bây giờ bạn phải đối phó với điều này ở giữa chuỗi, như các chuỗi vô nghĩa được gọi là mo moibibake.

# Ví dụ về mojibake
& macr; \\ _ (ã \ x83 \ x84) _ / & macr;
\ ufeffParty
\ 001 \ 033 [36; 44mI & # x92; m

May mắn thay, ftfy sử dụng phương pháp phỏng đoán để phát hiện và hoàn tác mojibake, với tỷ lệ dương tính giả rất thấp. Hãy để chúng tôi thấy những chuỗi của chúng tôi ở trên có thể được chuyển đổi thành, vì vậy chúng tôi có thể đọc nó. Phương thức chính là fix lòng () và bạn sẽ sử dụng phương thức đó để thực hiện giải mã.

nhập khẩu ftfy
foo = '& macr; \\ _ (ã \ x83 \ x84) _ / & macr;'
thanh = '\ ufeffParty'
baz = '\ 001 \ 033 [36; 44mI & # x92; m'
in (ftfy.fix lòng (foo))
in (ftfy.fix lòng (thanh))
in (ftfy.fix lòng (baz))

Nếu bạn muốn xem cách giải mã được thực hiện, hãy thử ftfy.explain_unicode (). Tôi không nghĩ rằng điều này sẽ rất hữu ích, nhưng thật thú vị khi thấy quá trình này.

ftfy.explain_unicode (foo)
U + 0026 & [Po] AMPERSAND
U + 006D m [Ll] LATIN NHỎ
U + 0061 a [Ll] LATIN NHỎ A
U + 0063 c [Ll] LATIN NHỎ THƯ C
U + 0072 r [Ll] LATIN NHỎ THƯỞNG
U + 003B; [Po] SEMICOLON
U + 005C \ [Po] GIẢI PHÁP GIẢI QUYẾT
U + 005F _ [Pc] LINE THẤP
U + 0028 ([Ps] PHỤ HUYNH TRÁI
U + 00E3 ã [Ll] LATIN NHỎ LỚP A VỚI TILDE
U + 0083 \ x83 [Cc] 
U + 0084 \ x84 [Cc] 
U + 0029) [Pe] PHỤ HUYNH QUYỀN
U + 005F _ [Pc] LINE THẤP
U + 002F / [Po] RẮN
U + 0026 & [Po] AMPERSAND
U + 006D m [Ll] LATIN NHỎ
U + 0061 a [Ll] LATIN NHỎ A
U + 0063 c [Ll] LATIN NHỎ THƯ C
U + 0072 r [Ll] LATIN NHỎ THƯỞNG
U + 003B; [Po] SEMICOLON
không ai

Dedupe

Đây là một thư viện sử dụng học máy để thực hiện khử trùng lặp và phân giải thực thể một cách nhanh chóng trên dữ liệu có cấu trúc. Có một bài viết tuyệt vời ở đây đi sâu vào chi tiết hơn nhiều so với tôi và tôi đã rút ra rất nhiều.

Chúng tôi sẽ thông qua Tải xuống dữ liệu Vị trí Thời thơ ấu của Chicago, có thể tìm thấy ở đây. Nó có một loạt các giá trị bị thiếu và các giá trị trùng lặp từ các nguồn dữ liệu khác nhau, vì vậy nó rất tốt để tìm hiểu.

Nếu bạn đã từng trải qua các dữ liệu trùng lặp trước đây, điều này sẽ trông rất quen thuộc.

# Cột và số lượng giá trị còn thiếu trong mỗi cột
Id có 0 giá trị na
Nguồn có 0 giá trị na
Tên trang web có 0 giá trị na
Địa chỉ có 0 giá trị na
Zip có 1333 giá trị na
Điện thoại có 146 giá trị na
Fax có 3299 giá trị na
Tên chương trình có giá trị na na 2009
Độ dài của ngày có giá trị na na 2009
ID nhà cung cấp IDHS có 3298 na giá trị
Đại lý có 3325 na giá trị
Vùng lân cận có 2754 giá trị na
Ghi danh được tài trợ có 2424 giá trị na
Tùy chọn chương trình có 2800 giá trị na
Số lượng trên mỗi trang web EHS có 3319 na giá trị
Số lượng trên mỗi trang web HS có 3319 na giá trị
Giám đốc có 3337 na giá trị
Head Start Fund có 3337 na giá trị
Eearly Head Start Fund có 2881 na giá trị
Quỹ CC có 2818 na giá trị
Progmod có 2818 na giá trị
Trang web có 2815 giá trị na
Giám đốc điều hành có 3114 giá trị na
Giám đốc trung tâm có 2874 na giá trị
Các chương trình có sẵn của ECE có 2379 giá trị na
NAEYC hợp lệ cho đến khi có 2968 giá trị na
Id chương trình NAEYC có 3337 giá trị na
Địa chỉ Email có 3203 giá trị na
Mô tả phòng ngừa của Ounce có 3185 giá trị na
Loại dịch vụ chất kết dính màu tím có 3215 na giá trị
Cột có 3337 giá trị na
Cột2 có 3018 giá trị na

Phương pháp preProcess được cung cấp bởi depupe là cần thiết để đảm bảo các lỗi don don xảy ra trong các giai đoạn lấy mẫu và huấn luyện của mô hình. Hãy tin tôi, sử dụng điều này sẽ làm cho việc sử dụng khấu trừ dễ dàng hơn nhiều. Lưu phương pháp này trong gói dọn dẹp cục bộ của bạn để bạn có thể sử dụng nó trong tương lai khi xử lý dữ liệu trùng lặp.

gấu trúc nhập khẩu như pd
nhập khẩu numpy
khấu trừ nhập khẩu
nhập khẩu os
nhập khẩu csv
nhập khẩu lại
từ unidecode nhập unidecode
def preProcess (cột):
    '' '
    Được sử dụng để ngăn ngừa lỗi trong quá trình khấu trừ.
    '' '
    thử :
        cột = cột.decode ('utf8')
    ngoại trừ AttributionError:
        vượt qua
    cột = unidecode (cột)
    cột = re.sub ('+', '', cột)
    cột = re.sub ('\ n', '', cột)
    cột = cột.strip (). dải ('"'). dải (" '"). low (). dải ()
    
    nếu không cột:
        cột = Không
    cột trả về

Bây giờ bắt đầu nhập cột .csv theo cột, trong khi xử lý dữ liệu.

def readData (tên tệp):
    
    dữ liệu_d = {}
    với mở (tên tệp) là f:
        người đọc = csv.DictReader (f)
        cho hàng trong trình đọc:
            Clean_row = [(k, preProcess (v)) cho (k, v) trong row.items ()]
            row_id = int (hàng ['Id'])
            data_d [row_id] = dict (clean_row)
trả lại df
name_of_file = 'data.csv'
in ('Làm sạch và nhập dữ liệu ...')
df = readData (name_of_file)

Bây giờ chúng ta cần nói với các tính năng mà chúng ta nên xem xét để xác định các giá trị trùng lặp. Dưới đây, mỗi tính năng được biểu thị theo trường và được gán một loại dữ liệu và nếu nó có bất kỳ giá trị thiếu nào. Có một danh sách toàn bộ các loại biến khác nhau mà bạn có thể sử dụng ở đây, nhưng để giữ cho nó dễ dàng, chúng tôi sẽ gắn bó với các chuỗi ngay bây giờ.

Tôi cũng sẽ không sử dụng mỗi cột đơn lẻ để xác định trùng lặp, nhưng bạn có thể nếu bạn nghĩ rằng điều đó sẽ giúp việc xác định các giá trị trong khung dữ liệu của bạn dễ dàng hơn.

# Đặt trường
các trường = [
        {'trường': 'Nguồn', 'loại': 'Đặt'},
        {'trường': 'Tên trang web', 'loại': 'Chuỗi'},
        {'trường': 'Địa chỉ', 'loại': 'Chuỗi'},
        {'trường': 'Zip', 'loại': 'Chính xác', 'bị thiếu': Đúng},
        {'trường': 'Điện thoại', 'loại': 'Chuỗi', 'bị thiếu': True},
        {'trường': 'Địa chỉ email', 'loại': 'Chuỗi', 'bị thiếu': True},
        ]

Bây giờ hãy để Lốc bắt đầu cho ăn một số dữ liệu.

# Đạt trong mô hình của chúng tôi
depuper = depupe.Dedupe (các lĩnh vực)
# Kiểm tra xem nó có hoạt động không
người khấu trừ
>>
# Cung cấp một số dữ liệu mẫu trong ... 15000 hồ sơ
depuper.sample (df, 15000)

Bây giờ chúng tôi về phần ghi nhãn. Khi bạn chạy phương thức này bên dưới, bạn sẽ được nhắc nhở bằng cách suy luận để thực hiện một số ghi nhãn đơn giản.

depupe.consoleLabel (người suy luận)
Những gì bạn nên xem; đào tạo thủ công

Thời điểm ‘a ha! Hiện thực là khi bạn nhận được lời nhắc này. Đây là suy luận yêu cầu bạn đào tạo nó, vì vậy nó biết những gì cần tìm kiếm. Bạn biết một giá trị trùng lặp sẽ trông như thế nào, vì vậy chỉ cần truyền đạt kiến ​​thức đó.

Những hồ sơ này đề cập đến cùng một điều?
(y) es / (n) o / (u) nsure / (f) đã chết

Bây giờ bạn không còn phải tìm kiếm thông qua hàng tấn hồ sơ để xem liệu sự trùng lặp đã xảy ra. Thay vào đó, một mạng lưới thần kinh đang được bạn đào tạo để tìm các bản sao trong khung dữ liệu.

Sau khi bạn cung cấp cho nó một số nhãn, kết thúc quá trình đào tạo và lưu tiến trình của bạn. Bạn có thể quay lại mạng lưới thần kinh của mình sau nếu thấy bạn có các đối tượng khung dữ liệu lặp đi lặp lại cần khấu trừ.

depuper.train ()
# Lưu đào tạo
với mở (training_file, 'w') là tf:
        depuper.writeTraining (tf)
# Lưu các thiết lập
với open (settings_file, 'wb') là sf:
        depuper.writeSinstall (sf)

Chúng tôi gần như đã hoàn thành, vì tiếp theo chúng tôi cần đặt ngưỡng cho dữ liệu của mình. Khi rec_ weight bằng 1, chúng ta sẽ nói với người suy luận về giá trị thu hồi bằng chính xác. Tuy nhiên, nếu rec_ weight = 3, chúng tôi sẽ đánh giá cao gấp ba lần. Bạn có thể chơi với các cài đặt này để xem những gì phù hợp nhất với bạn.

ngưỡng = depuper.thr Ngưỡng (df, rec_ weight = 1)

Cuối cùng, bây giờ chúng ta có thể tìm kiếm thông qua df của chúng tôi và xem các bản sao đang ở đâu. Đó là một thời gian dài để có được vị trí này, nhưng điều này tốt hơn nhiều so với làm điều này bằng tay.

# Phân cụm các bản sao lại với nhau
clustered_dupes = depuper.match (data_d, ngưỡng)
print ('Có {} bộ trùng lặp'.format (len (clustered_dupes)))

Vì vậy, hãy để một cái nhìn về các bản sao của chúng tôi.

phân cụm
>>
[((0, 1, 215, 509, 510, 1225, 1226, 1879, 2758, 3255),
  mảng ([0,88552043, 0,88552043, 0,77351897, 0,88552043, 0,88552043,
         0.88552043, 0.88552043, 0.89765924, 0.75684386, 0.83023088])),
 ((2, 3, 216, 511, 512, 1227, 1228, 2687), ...

Hum, mà không nói với chúng tôi nhiều. Trên thực tế, những gì đang cho chúng ta thấy? Điều gì đã xảy ra với tất cả các giá trị của chúng tôi?

Nếu bạn xem xét kỹ các giá trị (0, 1, 215, 509, 510, 1225, 1226, 1879, 2758, 3255) thì tất cả các vị trí id của bộ suy luận trùng lặp đều thực sự có cùng giá trị. Và, chúng ta có thể nhìn vào dữ liệu gốc để xác minh điều này.

{'Id': '215',
 'Nguồn': 'cps_early_childhood_portal_scrape.csv',
 'Tên trang web': 'đền thờ quân đội cứu rỗi',
 'Địa chỉ': '1 n. ogden ',
...
{'Id': '509',
 'Nguồn': 'cps_early_childhood_portal_scrape.csv',
 'Tên trang web': 'đội quân cứu rỗi - đền thờ / đội quân cứu rỗi',
 'Địa chỉ': '1 n ogden ave',
 'Zip': Không,
..

Điều này trông giống như trùng lặp với tôi. Đẹp.

Có nhiều cách sử dụng bộ suy luận nâng cao hơn, chẳng hạn như matchBlocks cho chuỗi các cụm hoặc các trường Tương tác trong đó tương tác giữa hai trường không chỉ là phụ mà là nhân. Điều này đã được thực hiện rất nhiều, vì vậy tôi sẽ để lại lời giải thích cho bài viết trên.

Kết hợp chuỗi với fuzzywuzzy

Hãy thử thư viện này. Nó rất thú vị bởi vì nó cho bạn điểm số về mức độ gần gũi của chuỗi khi chúng được so sánh.

Đây là một công cụ tuyệt vời, vì trước đây tôi đã thực hiện các dự án mà tôi cần dựa vào addon fuzzymatch của Google Sheet để chẩn đoán các vấn đề xác thực dữ liệu - nghĩ rằng các quy tắc CRM không được áp dụng hoặc hành động chính xác - và cần phải làm sạch hồ sơ để làm bất kỳ loại phân tích.

Nhưng, đối với các tập dữ liệu lớn, cách tiếp cận này không ổn định.

Tuy nhiên, với fuzzywuzzy, bạn có thể bắt đầu kết hợp chuỗi trong một vấn đề khoa học hơn. Không phải để quá kỹ thuật, nhưng nó sử dụng một cái gì đó gọi là khoảng cách Levenshtein khi so sánh. Đây là một số liệu tương tự chuỗi cho hai chuỗi, sao cho khoảng cách giữa là số lần chỉnh sửa ký tự đơn được yêu cầu để thay đổi một từ này sang từ khác.

Ví dụ. nếu bạn muốn thay đổi chuỗi foo thành thanh, số lượng ký tự tối thiểu cần thay đổi sẽ là 3 và điều này được sử dụng để xác định ‘khoảng cách.

Hãy cùng xem cách thức hoạt động của nó trong thực tế.

$ pip3 cài đặt mờ
# test.txt
từ fuzzwuzzy nhập fuzz
từ quy trình nhập mờ
foo = 'là chuỗi này'
thanh = 'như chuỗi đó?'
fuzz.ratio (foo, thanh)
>>
71
fuzz.WRatio (foo, bar) # Tỷ lệ trọng số
>>
73
fuzz.UQRatio (foo, bar) # Tỷ lệ nhanh Unicode
>> 73

Gói fuzzywuzzy có các cách khác nhau để đánh giá các chuỗi (WRatio, UQRatio, v.v.) và tôi sẽ chỉ gắn bó với việc triển khai tiêu chuẩn cho bài viết này.

Tiếp theo, chúng ta có thể xem xét một chuỗi mã thông báo, trả về một số đo các chuỗi tương tự giữa độ 0 và 100 nhưng sắp xếp mã thông báo trước khi so sánh. Đây là chìa khóa vì bạn có thể chỉ muốn xem nội dung của chuỗi, thay vì vị trí của chúng.

Các chuỗi foo và thanh có cùng mã thông báo nhưng có cấu trúc khác nhau. Bạn có muốn đối xử với họ như nhau? Bây giờ bạn có thể dễ dàng xem và tính đến loại khác biệt này trong dữ liệu của mình.

foo = 'đây là một foo'
thanh = 'foo a là đây'
fuzz.ratio (foo, thanh)
>>
31
fuzz.token_sort_ratio ('đây là một foo', 'foo a là đây')
>>
100

Hoặc tiếp theo, bạn cần tìm kết quả khớp gần nhất của chuỗi từ danh sách các giá trị. Trong trường hợp này, chúng tôi sẽ xem xét các tựa game Harry Potter.

Thế còn cuốn sách Harry Potter với tiêu đề gì đó thì nó có thể là I I dunno. Tôi chỉ cần đoán và xem một trong những cuốn sách này đạt điểm gần nhất với dự đoán của tôi.

Tôi đoán là ‘fire, và hãy để xem cách nó ghi điểm so với danh sách các danh hiệu có thể có.

lst_to_eval = ['Harry Potter và hòn đá triết gia',
'Harry Potter và phòng chứa bí mật',
'Harry Potter và tù nhân ngục Azkaban',
'Harry Potter và chiếc cốc lửa',
'Harry Potter và Hội Phượng hoàng',
'Harry Potter và hoàng tử lai',
'Harry Potter và bảo bối tử thần']
# Hai câu trả lời hàng đầu dựa trên dự đoán của tôi
process.extract ("lửa", lst_to_eval, giới hạn = 2)
>>
[('Harry Potter và Chiếc cốc lửa', 60), ("Harry Potter và hòn đá phù thủy", 30)
results = process.extract ("fire", lst_to_eval, giới hạn = 2)
cho kết quả trong kết quả:
  print ('{}: có số điểm là {}'. format (kết quả [0], kết quả [1]))
>>
Harry Potter và Chiếc cốc lửa: có số điểm 60
Harry Potter và hòn đá phù thủy: có số điểm 30

Hoặc nếu bạn chỉ muốn trả lại một, bạn có thể.

>>> process.extractOne ("đá", lst_to_eval)
("Harry Potter và hòn đá phù thủy", 90)

Tôi biết chúng ta đã nói về suy luận trước đó, nhưng đây là một ứng dụng khác của quá trình tương tự với fuzzywuzzy. Chúng ta có thể lấy một danh sách các chuỗi chứa các bản sao và sử dụng kết hợp mờ để xác định và loại bỏ các bản sao.

Không lạ mắt như một mạng lưới thần kinh, nhưng nó sẽ thực hiện công việc cho các hoạt động nhỏ.

Chúng tôi sẽ tiếp tục với chủ đề Harry Potter và tìm kiếm các nhân vật trùng lặp từ các cuốn sách trong một danh sách.

Bạn cần phải đặt ngưỡng trong khoảng từ 0 đến 100. Khi ngưỡng giảm số lượng trùng lặp được tìm thấy sẽ tăng lên, vì vậy danh sách được trả về sẽ bị rút ngắn. Mặc định là 70.

# Danh sách tên nhân vật trùng lặp
chứa_dupes = [
'Harry Potter',
'H. Potter ',
'Harry James Potter',
'James Potter',
'Ronald Bilius \' Ron \ 'Weasley',
'Ron Weasley',
'Ronald Weasley']
# In các giá trị trùng lặp
process.dedupe (chứa_dupes)
>>
dict_keys (['Harry James Potter', "Ronald Bilius 'Ron' Weasley"])
# In các giá trị trùng lặp với ngưỡng cao hơn
process.dedupe (chứa_dupes, ngưỡng = 90)
>>
dict_keys (['Harry James Potter', 'H. Potter', "Ronald Bilius 'Ron' Weasley"])

Và, như một phần thưởng nhanh chóng, bạn cũng có thể thực hiện một số kết hợp mờ với gói datetime để trích xuất ngày từ một chuỗi văn bản. Điều này thật tuyệt khi bạn không muốn viết (một lần nữa) viết biểu thức regex.

từ parse nhập liệu Dateutil.parser
dt = parse ("Hôm nay là ngày 1 tháng 1 năm 2047 lúc 8:21:00 sáng", fuzzy = True)
in (dt)
>>
2047-01-01 08:21:00
dt = parse ("18 tháng 5 năm 2049 một cái gì đó", fuzzy = True)
in (dt)
>>
2049-05-18 00:00:00

Hãy thử một số sklearn

Cùng với việc làm sạch dữ liệu, bạn cũng cần chuẩn bị dữ liệu để nó ở dạng bạn có thể đưa vào mô hình của mình. Hầu hết các ví dụ ở đây được lấy trực tiếp từ tài liệu, cần được kiểm tra vì nó thực sự làm tốt công việc giải thích thêm về tính mới của mỗi gói.

Chúng tôi sẽ nhập gói tiền xử lý trước, sau đó nhận các phương thức bổ sung từ đó khi chúng tôi thực hiện. Ngoài ra, tôi có thể sử dụng sklearn phiên bản 0.20.0, vì vậy nếu bạn có vấn đề với việc nhập một số gói thì hãy kiểm tra phiên bản của bạn.

Chúng tôi sẽ làm việc với hai loại dữ liệu khác nhau, str và int chỉ để làm nổi bật cách các kỹ thuật tiền xử lý khác nhau hoạt động.

# Khi bắt đầu dự án
từ quá trình nhập trước sklearn
# Và hãy tạo một mảng ints ngẫu nhiên để xử lý
ary_int = np.random.randint (-100, 100, 10)
ary_int
>> [5, -41, -67, 23, -53, -57, -36, -25, 10, 17]
# Và một số str để làm việc với
ary_str = ['foo', 'thanh', 'baz', 'x', 'y', 'z']

Hãy để thử một số nhãn nhanh với LabelEncoder trên ary_str của chúng tôi. Điều này rất quan trọng vì bạn có thể chỉ cần cung cấp các chuỗi thô - bạn cũng có thể nhưng điều đó nằm ngoài phạm vi của bài viết này - trong các mô hình của bạn. Vì vậy, chúng tôi sẽ mã hóa nhãn cho từng chuỗi, với giá trị từ 0 đến n. Trong ary_str của chúng tôi, chúng tôi có 6 giá trị duy nhất nên phạm vi của chúng tôi sẽ là 0 - 5.

từ sklearn.pre processing LabelEncoder
l_encoder = tiền xử lý. Nhãn hiệu ()
l_encoder.fit (ary_str)
>> Trình ghi nhãn ()
# Giá trị của chúng tôi là gì?
l_encoder.transform (['foo'])
>> mảng ([2])
l_encoder.transform (['baz'])
>> mảng ([1])
l_encoder.transform (['bar'])
>> mảng ([0])

Bạn sẽ nhận thấy những thứ này không được đặt hàng, vì ngay cả khi foo xuất hiện trước thanh trong mảng, nó được mã hóa bằng 2 trong khi thanh được mã hóa bằng 1. Chúng tôi sẽ sử dụng một phương thức mã hóa khác khi chúng tôi cần đảm bảo các giá trị của chúng tôi được mã hóa theo đúng thứ tự.

Nếu bạn có nhiều danh mục để theo dõi, bạn có thể quên bản đồ str tới int. Đối với điều đó, chúng ta có thể tạo ra một dict.

# Kiểm tra bản đồ
danh sách (l_encoder. classes_)
>> ['thanh', 'baz', 'foo', 'x', 'y', 'z']
# Tạo từ điển ánh xạ
dict (zip (l_encoder. classes_, l_encoder.transform (l_encoder. classes_)))
>> {'thanh': 0, 'baz': 1, 'foo': 2, 'x': 3, 'y': 4, 'z': 5}

Quá trình này hơi khác một chút nếu bạn có một khung dữ liệu, nhưng thực sự dễ dàng hơn một chút. Bạn chỉ cần .apply () đối tượng LabelEncoder vào DataFrame. Đối với mỗi cột, bạn sẽ nhận được một nhãn duy nhất cho các giá trị trong cột đó. Lưu ý cách foo được mã hóa thành 1, nhưng y cũng vậy.

# Hãy thử LabelEncoder trên một khung dữ liệu
gấu trúc nhập khẩu như pd
l_encoder = tiền xử lý. Nhãn hiệu () # Đối tượng mới
df = pd.DataFrame (data = {'col1': ['foo', 'bar', 'foo', 'bar'],
                          'col2': ['x', 'y', 'x', 'z'],
                          'col3': [1, 2, 3, 4]})
# Bây giờ cho phần dễ dàng
df.apply (l_encoder.fit_transform)
>>
   col1 col2 col3
0 1 0 0
1 0 1 1
2 1 0 2
3 0 2 3

Bây giờ, chúng tôi chuyển sang mã hóa thứ tự trong đó các tính năng vẫn được biểu thị dưới dạng giá trị nguyên, nhưng chúng có ý nghĩa về vị trí và cấu trúc. Như vậy x đến trước y và y đến trước z.

Tuy nhiên, chúng tôi sẽ ném cờ lê vào đây. Không chỉ các giá trị được sắp xếp, mà chúng sẽ được ghép với nhau.

Chúng tôi sẽ lấy hai mảng giá trị [‘foo,’ bar, ’baz,] và [’ x,, ’y,‘ z,]. Tiếp theo, chúng tôi sẽ mã hóa 0, 1 và 2 cho từng bộ giá trị trong mỗi mảng và tạo một cặp được mã hóa cho mỗi giá trị.

Ví dụ. [‘Foo,, z z] sẽ được ánh xạ tới [0, 2] và [‘ baz, ’x,] sẽ được ánh xạ tới [2, 0].

Đây là một cách tiếp cận tốt để thực hiện khi bạn cần lấy một loạt các danh mục và làm cho chúng có sẵn để hồi quy và đặc biệt tốt khi bạn có các chuỗi chuỗi xen kẽ - các danh mục riêng biệt vẫn chồng chéo với nhau - và cần biểu diễn trong khung dữ liệu .

từ sklearn.pre processing nhập OrdinalEncoder
o_encoder = OrdinalEncoder ()
ary_2d = [['foo', 'thanh', 'baz'], ['x', 'y', 'z']]
o_encoder.fit (2d_ary) # Phù hợp với các giá trị
o_encoder.transform ([['foo', 'y']])
>> mảng ([[0., 1.]])

Mã hóa cổ điển nóng hoặc ummy giả, trong đó các tính năng đơn lẻ của các danh mục sau đó được biểu thị dưới dạng các cột bổ sung 0 hoặc 1, tùy thuộc vào giá trị đó có xuất hiện hay không. Quá trình này tạo ra một cột nhị phân cho mỗi thể loại và trả về một ma trận thưa thớt hoặc mảng dày đặc.

Tín dụng vào https://blog.myyellowroad.com/

Tại sao thậm chí sử dụng này? Bởi vì loại mã hóa này là cần thiết để cung cấp dữ liệu phân loại cho nhiều mô hình scikit như mô hình hồi quy tuyến tính và SVM. Vì vậy, hãy thoải mái với điều này.

từ sklearn.pre processing nhập OneHotEncoder
hot_encoder = OneHotEncoder (xử lý_unknown = 'bỏ qua')
hot_encoder.fit (ary_2d)
hot_encoder. Chuyên mục_
>>
[mảng (['foo', 'x'], dtype = object), mảng (['bar', 'y'], dtype = object), mảng (['baz', 'z'], dtype = object )]
hot_encoder.transform ([['foo', 'foo', 'baz'], ['y', 'y', 'x']]). toarray ()
>>
mảng ([[1., 0., 0., 0., 1., 0.],
       [0., 0., 0., 1., 0., 0.]])

Nếu chúng ta có một khung dữ liệu để làm việc thì sao?

Chúng ta vẫn có thể sử dụng một mã hóa nóng? Nó thực sự dễ dàng hơn nhiều so với bạn nghĩ khi bạn chỉ cần sử dụng .get_dummies () có trong gấu trúc.

pd.get_dummies (df)
      col3 col1_bar col1_foo col2_x col2_y col2_z
0 1 0 1 1 0 0
1 2 1 0 0 1 0
2 3 0 1 1 0 0
3 4 1 0 0 0 1

Hai trong số ba cột trong df đã được tách ra và mã hóa nhị phân thành một khung dữ liệu.

Ví dụ. cột col1_bar là col1 từ df, nhưng có 1 là giá trị bản ghi khi thanh là giá trị trong khung dữ liệu gốc.

Điều gì về khi các tính năng của chúng tôi cần phải được chuyển đổi trong một phạm vi nhất định. Bằng cách sử dụng MinMaxScaler, mỗi tính năng có thể được thu nhỏ riêng lẻ sao cho nó nằm trong phạm vi nhất định. Theo mặc định, các giá trị nằm trong khoảng từ 0 đến 1, nhưng bạn có thể thay đổi phạm vi.

từ sklearn.pre processing nhập MinMaxScaler
mm_scaler = MinMaxScaler (Feature_range = (0, 1)) # Giữa 0 và 1
mm_scaler.fit ([ary_int])
>> MinMaxScaler (sao chép = Đúng, tính năng_range = (0, 1))
in (scaler.data_max_)
>> [5. -41. -67. 23. -53. -57. -36. -25. 10. 17.]
in (mm_scaler.fit_transform ([ary_int]))
>> [[0. 0. 0. 0. 0. 0. 0. 0. 0. 0.] # Humm có gì đó không đúng

Nếu bạn nhận thấy đầu ra có thể là tất cả số không, đó không phải là thứ chúng ta muốn. Có một lời giải thích tốt ở đây và đây, về lý do tại sao điều đó sẽ xảy ra, nhưng câu chuyện ngắn là, mảng được định dạng không chính xác.

Đó là ma trận (1, n) và cần được chuyển đổi thành ma trận (n, 1). Cách dễ nhất để làm điều này là đảm bảo mảng của bạn là một mảng gọn gàng, vì vậy bạn có thể thao tác hình dạng.

# Tạo mảng numpy
ary_int = np.array ([5, -41, -67, 23, -53, -57, -36, -25, 10, 17])
# Biến đổi
mm_scaler.fit_transform (ary_int [:, np.newaxis])
>>
mảng ([0,8],
       [0.28888889],
       [0. ],
       [1. ],
       [0.15555556],
       [0.11111111],
       [0,34444444],
       [0.46666667],
       [0.85555556],
       [0,93333333]])
# Bạn cũng có thể dùng
mm_scaler.fit_transform (ary_int.reshape (-1, 1))
# Cũng thử một quy mô khác
mm_scaler = MinMaxScaler (Feature_range = (0, 10))
mm_scaler.fit_transform (ary_int.reshape (-1, 1))
>>
mảng ([[8.],
       [2.88888889],
       [0.],
       [10. ],
       [1.55555556],
       [1.11111111],
       [3.44444444],
       [4.66666667],
       [8,55555556],
       [9.33333333]])

Bây giờ chúng ta có thể nhanh chóng mở rộng quy mô dữ liệu của mình, còn việc triển khai một số hình dạng cho dữ liệu được chuyển đổi của chúng ta thì sao? Chúng tôi đang xem xét tiêu chuẩn hóa dữ liệu, sẽ cung cấp cho bạn các giá trị tạo ra một gaussian với giá trị trung bình là 0 và sd là 1. Bạn có thể xem xét phương pháp này khi thực hiện giảm độ dốc hoặc nếu bạn cần các đầu vào có trọng số như hồi quy và mạng lưới thần kinh. Ngoài ra, nếu bạn sẽ thực hiện KNN, trước tiên hãy chia tỷ lệ dữ liệu của bạn. Lưu ý cách tiếp cận này khác với bình thường hóa, vì vậy don lồng bị nhầm lẫn.

Đơn giản chỉ cần sử dụng quy mô từ tiền xử lý.

tiền xử lý.scale (foo)
>> mảng ([0.86325871, -0.58600774, -1.40515833, 1.43036297, -0.96407724, -1,090141,
tiền xử lý.scale (foo) .mean ()
>> -4.4408920985006264e-17 # Về cơ bản là không
 tiền xử lý.scale (foo) .std ()
>> 1.0 # Chính xác những gì chúng ta muốn

Gói sklearn cuối cùng để xem xét là Binarizer, bạn vẫn nhận được 0 và 1 thông qua điều này nhưng bây giờ chúng được xác định theo các điều khoản của riêng bạn. Đây là quá trình ‘ngưỡng các tính năng số để có được các giá trị boolean. Ngưỡng giá trị lớn hơn ngưỡng sẽ ánh xạ thành 1, trong khi các giá trị to sẽ ánh xạ tới 0. Đồng thời, đây là quy trình phổ biến khi tiền xử lý văn bản để có được tần số thuật ngữ trong tài liệu hoặc kho văn bản.

Hãy nhớ rằng, cả fit () và Transform () đều yêu cầu mảng 2d, đó là lý do tại sao tôi đã lồng ary_int trong một mảng khác. Trong ví dụ này, tôi đã đặt ngưỡng là -25, vì vậy bất kỳ số nào ở trên mức đó sẽ được gán 1.

từ sklearn.pre Processing nhập Binarizer
# Đặt -25 làm ngưỡng của chúng tôi
tz = Binarizer (ngưỡng = -25.0) .fit ([ary_int])
tz.transform ([ary_int])
>> mảng ([[1, 0, 0, 1, 0, 0, 0, 0, 1, 1]])

Bây giờ chúng ta có một vài kỹ thuật khác nhau, cái nào là tốt nhất cho thuật toán của bạn? Nó có thể tốt nhất để lưu một vài datafram trung gian khác nhau với dữ liệu được chia tỷ lệ, dữ liệu đã được đánh dấu, v.v. để bạn có thể thấy hiệu ứng trên đầu ra của mô hình của bạn.

Suy nghĩ cuối cùng

Làm sạch và chuẩn bị dữ liệu là không thể tránh khỏi và nói chung là một nhiệm vụ vô ơn khi nói đến khoa học dữ liệu. Nếu bạn đủ may mắn để có một nhóm kỹ sư dữ liệu với bạn, người có thể giúp thiết lập các đường ống ETL để làm cho công việc của bạn dễ dàng hơn, thì bạn có thể thuộc nhóm thiểu số các nhà khoa học dữ liệu.

Cuộc sống không chỉ là một loạt các bộ dữ liệu Kaggle, trong thực tế, bạn sẽ phải đưa ra quyết định về cách truy cập và làm sạch dữ liệu bạn cần hàng ngày. Đôi khi, bạn sẽ có rất nhiều thời gian để đảm bảo mọi thứ được đặt đúng chỗ, nhưng hầu hết thời gian bạn sẽ bị ép để trả lời. Nếu bạn có các công cụ phù hợp và hiểu được những gì có thể, bạn sẽ có thể dễ dàng nhận được những câu trả lời đó.

Như mọi khi, tôi hy vọng bạn đã học được một cái gì đó mới.

Chúc mừng

Đọc thêm