(Acest articol a fost publicat pentru prima dată pe John Russellși cu amabilitate a contribuit la R-bloggeri). (Puteți raporta problema legată de conținutul acestei pagini aici)
Doriți să vă distribuiți conținutul pe R-bloggeri? dați clic aici dacă aveți un blog, sau aici dacă nu aveți.
Ca și familiile, seturile de date ordonate sunt toate la fel, dar fiecare set de date dezordonat este dezordonat în felul său. – Hadley Wickham
Lucrăm adesea cu seturi de date în care există un identificator unic care poate fi folosit pentru a lega sau filtra datele, implicând de obicei un anumit tip de alăturare.
Cu toate acestea, uneori identificatorii pe care dorim să îi folosim pentru a ne alătura sunt aproape chibrituri. De exemplu, poate vă alăturați unui set de date după nume, în cazul în care un set de date are Ioaniar setul de date la care vă alăturați are Ioan. Sau poate există erori de introducere a textului și este în schimb Jon.
Ceea ce aveți nevoie este o modalitate de a asocia datele care este puțin neclară. Introduceți excelentul lui (David Robinson)(https://github.com/dgrtwo/fuzzyjoin) fuzzyjoin
pachet.
Prezentarea unui exemplu – școlile din Insulele Virgine
Există 20 de școli listate în baza de date a școlilor publice pentru Centrul Național de Statistică a Educației din Insulele Virgine. Am descărcat setul de date și îl puteți extrage din depozitul meu github prin codul de mai jos. Un defilabil DT
tabel pentru a explora mai jos (dezactivând o mulțime de funcții doar pentru a vedea tabelul):
Cod în R
library(tidyverse) library(fuzzyjoin) library(kableExtra) VI <- read_csv("https://github.com/drjohnrussell/drjohnrussell.github.io/raw/refs/heads/master/posts/2025-01-17-fuzzyjoin-in-action/data/VIschools.csv") VI |> kbl() |> kable_paper() |> ##nice theme kable_styling(bootstrap_options = c("striped", "hover")) |> scroll_box(height = "200px") ##adds scrolling
Şcoala elementară Alfredo Andrews | 780000200002 | Districtul școlar Saint Croix | RFD 1 KINGSHILL | VI | PK | 06 | 495 |
Şcoala Primară Claude O. Markoe | 780000200006 | Districtul școlar Saint Croix | PARCELE 71 75 MARS HILL | VI | PK | 06 | 403 |
Eulalie Rivera | 780000200011 | Districtul școlar Saint Croix | RUTA 1 GROVE LOC | VI | PK | 08 | 645 |
Liceul Complex Educaţional St. Croix | 780000200013 | Districtul școlar Saint Croix | RR2 KINGSHILL | VI | 09 | 12 | 893 |
Juanita Gardine | 780000200021 | Districtul școlar Saint Croix | ESTATE RICHMOND | VI | PK | 08 | 305 |
Școala elementară Lew Muckle | 780000200023 | Districtul școlar Saint Croix | 317 FERMA SION | VI | PK | 06 | 339 |
Pearl B. Larsen | 780000200028 | Districtul școlar Saint Croix | MOSIUNE Sfantul Petru | VI | PK | 08 | 432 |
Școala Primară Ricardo Richards | 780000200029 | Districtul școlar Saint Croix | 491 PĂT STEAR | VI | PK | 06 | 392 |
Liceul Central St. Croix | 780000200030 | Districtul școlar Saint Croix | RSD 2 KINGSHILL | VI | 09 | 12 | 717 |
Liceul John H. Woodson | 780000200037 | Districtul școlar Saint Croix | RURAL RURAL 1 KINGSHILL | VI | 07 | 08 | 461 |
Liceul Charlotte Amalie | 780003000005 | Saint Thomas – Districtul școlar Saint John | 8 și 9 ESTATE THOMAS | VI | 09 | 12 | 1076 |
Liceul Ivanna Eudora Kean | 780003000015 | Saint Thomas – Districtul școlar Saint John | 1 și 2 ESTATE NAZARETH | VI | 09 | 12 | 738 |
Şcoala elementară Jane E. Tuitt | 780003000018 | Saint Thomas – Districtul școlar Saint John | 19 LEVOKI STRAEDE | VI | KG | 04 | 154 |
Scoala Primara Joseph Gomez | 780003000019 | Saint Thomas – Districtul școlar Saint John | 142 RETRAGERE ANNAS | VI | PK | 05 | 462 |
Şcoala elementară Joseph Sibilly | 780003000020 | Saint Thomas – Districtul școlar Saint John | 14 15 16 MOSIUNE ELIZABETH | VI | PK | 05 | 226 |
Şcoala Julius E. Sprauve | 780003000022 | Saint Thomas – Districtul școlar Saint John | 14 18 MOSIA ENIGHED | VI | PK | 08 | 225 |
Școala Elementară Lockhart | 780003000024 | Saint Thomas – Districtul școlar Saint John | 41 ESTATE THOMAS | VI | KG | 08 | 977 |
Şcoala Elementară Ulla F. Muller | 780003000026 | Saint Thomas – Districtul școlar Saint John | 7B CONTANT IMOBILĂ | VI | PK | 05 | 401 |
Şcoala elementară Yvonne E. Milliner-Bowsky | 780003000027 | Saint Thomas – Districtul școlar Saint John | 15B și 16 ESTATE MANDAHL | VI | PK | 05 | 433 |
Școala Gimnazială Bertha C. Boschulte | 780003000034 | Saint Thomas – Districtul școlar Saint John | 9 1 si 12A BOVONI | VI | 06 | 08 | 538 |
Să presupunem că avem un set de date cu următoarele nume de școli și dorim să extragem informații din NCES.
Cod în R
sample <- read_csv("https://github.com/drjohnrussell/drjohnrussell.github.io/raw/refs/heads/master/posts/2025-01-17-fuzzyjoin-in-action/data/sample.csv") sample |> kbl() |> kable_paper()
eulalie rivera | VI |
Şcoala elementară Joseph | VI |
Şcoala elementară Alfredo Andrews | NY |
Introduceți fuzzyjoin
pachet, care permite datelor să fie dezordonate în multe feluri, în funcție de ceea ce aveți nevoie. Unele dintre modalitățile de aderare prezentate în pachet sunt următoarele:
- difference_join – îmbinări care sunt numerice și pe o distanță specificată
- geo_join – îmbinări care utilizează distanțe bazate pe latitudine și longitudine
- regex_join – îmbinări care caută modele regex comune (text și poziție)
- stringdist_join – îmbinări care iau în considerare micile diferențe ale șirului
Să ne concentrăm asupra stringdist_join
pentru cazuri speciale de utilizare.
Uniri care ignoră majuscule
Unele care ignoră cazul, în care nu trebuie să mutați folosind ceva de genul stringr str_to_lower pe date pentru a le schimba este un mare câștig. Îl putem folosi pentru a se potrivi eulalie rivera.
Iată ce s-ar întâmpla așa cum este:
Cod în R
sample(1,1) |> inner_join(VI,by=c("schoolname")) |> kbl() |> kable_paper()
Pe de altă parte, putem folosi stringdist_join
și setați ignore_case
a egala ADEVĂRAT.
Cod în R
sample(1,1) |> stringdist_join(VI, by=c("schoolname"), max_dist=0, mode="inner", ignore_case=TRUE) |> kbl() |> kable_paper()
eulalie rivera | Eulalie Rivera | 780000200011 | Districtul școlar Saint Croix | RUTA 1 GROVE LOC | VI | PK | 08 | 645 |
Imbinari care profita de distanta sirurilor
Modul în care am profitat de acest lucru este în a trata greșelile de scriere sau datele în care cineva poate avea nume subtil diferite pentru o școală (de exemplu, unul are cuvântul şcoală în timp ce celălalt îl scapă). Ce este frumos la fuzzyjoin
pachetul este că puteți face aderarea. Ceea ce este mai puțin frumos este că vă cere să faceți o verificare a liniei după aceea, mai ales când sunteți liber cu distanțele.
Să ne uităm la al doilea rând, Şcoala Elementară Josephși au un maximum distance
din 8.
Cod în R
sample(2,1) |> stringdist_join(VI, by="schoolname", max_dist=8, mode="inner", ignore_case=TRUE, distance_col="stringdistance") |> kbl() |> kable_paper()
Şcoala elementară Joseph | Scoala Primara Joseph Gomez | 7.80003e+11 | Saint Thomas – Districtul școlar Saint John | 142 ANNAS RETRAGER | VI | PK | 05 | 462 | 6 |
Şcoala elementară Joseph | Şcoala elementară Joseph Sibilly | 7.80003e+11 | Saint Thomas – Districtul școlar Saint John | 14 15 16 MOSIUNE ELIZABETH | VI | PK | 05 | 226 | 8 |
Şcoala elementară Joseph | Școala Elementară Lockhart | 7.80003e+11 | Saint Thomas – Districtul școlar Saint John | 41 ESTATE THOMAS | VI | KG | 08 | 977 | 7 |
Puteți vedea puterea și pericolul fuzzyjoin
pachet aici. Este uimitor că preia cele două școli care îl au și pe Iosif în numele lor, dar sugerează și că ai putea schimba câteva litere la început și ai forma numele unei alte școli.
Când am folosit fuzzyjoin, am aranja datele după numele școlii și apoi variabila distance_col, astfel încât să putem face cu ușurință o verificare de linie și să alegem cea mai bună potrivire (dacă este disponibilă).
Potrivire din mai multe coloane
Ca o notă secundară, este plăcut să utilizați fuzzyjoin
pachet pentru a vedea erorile în mai multe coloane. Aici putem vedea cum funcționează cu al treilea rând al setului de date.
Cod în R
sample(3,) |> stringdist_join(VI, by=c("schoolname","state"), mode="inner", max_dist = 4, ignore_case=TRUE, distance_col="stringdistance") |> kbl() |> kable_paper()
Şcoala elementară Alfredo Andrews | NY | Şcoala elementară Alfredo Andrews | 780000200002 | Districtul școlar Saint Croix | RFD 1 KINGSHILL | VI | PK | 06 | 495 | 0 | 2 | N / A |
Ceea ce este frumos este că, în revizuire, puteți vedea cu ușurință prin variabila distance_col unde au fost găsite modificările.
Alții au folosit fuzzyjoin
cu mare efect – sunt inspirat să citesc această vignetă în special despre geo_joins