Jak porównać dwa pliki CSV i znaleźć zmiany

Najszybszy sposób na porównanie dwóch plików CSV to wklejenie obu do narzędzia diff obok siebie, wyrównanie kolumn i odczytanie wierszy, które podświetla. Porównywanie to łatwa część. To szum sprawia ludziom problemy: przestawiony eksport, średnik zamiast przecinka albo wartość, którą ktoś ujął w cudzysłów, mogą sprawić, że dwa pliki zawierające te same dane będą wyglądać, jakby nie miały ze sobą nic wspólnego.

Ten przewodnik pokazuje, jak uzyskać czysty, wiarygodny diff CSV. Przyjrzymy się, dlaczego dwa równoważne eksporty rozjeżdżają się na papierze, które metody warto znać, oraz rozwiązanemu przykładowi, za którym możesz podążać. Jeśli chcesz tylko narzędzie, nasza strona porównywania CSV robi to w przeglądarce.

Dlaczego pliki CSV są zwodniczo trudne do porównania

CSV wygląda prosto, ale nie ma jednego ścisłego standardu. Najbliższy temu jest RFC 4180, a wiele rzeczywistych plików go nie przestrzega. Dwa eksporty tej samej tabeli mogą różnić się separatorem, cudzysłowami, znakami końca wiersza i kolejnością wierszy, opisując dokładnie te same dane. Zwykły diff tekstowy o tym nie wie, więc oznacza wszystko.

Oto kluczowa rzecz do rozstrzygnięcia przed rozpoczęciem: czy kolejność wierszy ma dla ciebie znaczenie? Eksport bazy danych posortowany według nazwy i ten sam eksport posortowany według ID zawierają identyczny zestaw rekordów, ale diff wierszowy pomaluje na czerwono i zielono prawie każdy wiersz. Jeśli wiersze mają stabilny klucz (kolumnę ID), wcześniejsze posortowanie obu plików według tego klucza znów czyni diff czytelnym.

Wygląda na zmianę, zwykle nią nie jest
Co widzisz w diffieCzy to prawdziwa zmiana?Co zrobić
Wiersze w innej kolejnościNie, jeśli dane to ten sam zestawPosortuj oba pliki według kolumny klucza
Separator przecinek vs. średnikNie, te same polaZnormalizuj do jednego separatora
Ada vs. "Ada"Nie, cudzysłowy są tu opcjonalneZnormalizuj cudzysłowy
Znaki końca wiersza CRLF vs. LFNieZnormalizuj znaki końca wiersza
Pusty wiersz na końcuNieUsuń go
Wartość komórki się zmieniłaTakZbadaj, to prawdziwa zmiana

Wiersz o separatorze łapie wielu ludzi, zwłaszcza między regionami: wiele europejskich ustawień lokalnych używa średnika, bo przecinek jest separatorem dziesiętnym. Te same dane, inny separator. Jeśli chcesz szczegół o tym, jak przeglądarki i narzędzia czytają tekst tabelaryczny, notatka MDN o odczytywaniu plików w przeglądarce to dobry punkt wyjścia.

Cztery sposoby porównywania CSV i kiedy po który sięgnąć

Nie ma jednej najlepszej metody. Zależy to od rozmiaru plików i od tego, czy kolejność wierszy ma znaczenie. Oto jak wypadają popularne opcje.

MetodaNajlepsza doWysiłekRozumie CSV?
Oglądanie na okoMaleńkie pliki, garstka wierszyNiskiNie, to ty jesteś parserem
Narzędzie diff onlineSzybkie sprawdzenia, wklejanie skądkolwiekNiskiWiersz po wierszu, tak
Aplikacja arkusza kalkulacyjnegoPrzegląd wizualny, formuły, filtrowanieŚredniTak, ale ręcznie
Wiersz poleceń (sort, csvkit)Duże pliki, skrypty, porównania według kluczaŚredniTak, gdy najpierw posortujesz

Dla większości ludzi narzędzie przeglądarkowe wygrywa szybkością: nic do instalowania, a eksport możesz wkleić prosto z pobranego pliku lub klienta bazy danych. Haczykiem jest szum kolejności wierszy i separatora, którym zajmiemy się dalej. Przy bardzo dużych plikach warto poznać csvkit w wierszu poleceń.

Najszybsze czyste porównanie, krok po kroku

To rutyna, której używam, gdy ktoś podaje mi dwa eksporty i pyta "co się różni?". Zajmuje to mniej niż minutę.

  1. Upewnij się, że oba pliki używają tego samego separatora i mają ten sam wiersz nagłówka.
  2. Jeśli kolejność wierszy nie ma znaczenia, najpierw posortuj oba pliki według kolumny klucza.
  3. Otwórz narzędzie do porównywania CSV.
  4. Wklej oryginał po lewej, a nową wersję po prawej.
  5. Odczytaj wynik. Zielony to dodany wiersz, czerwony to usunięty wiersz, a zmieniona komórka pojawia się jako jedno i drugie.

Krok drugi to cały sekret, gdy wiersze są nieuporządkowane. Gdy oba pliki są posortowane w ten sam sposób, jedyne, co pozostaje do podświetlenia, to wiersze, które naprawdę się zmieniły. Nasz silnik diff jest zbudowany na diff-match-patch od Google, który najpierw porównuje wiersz po wierszu, więc pozostaje szybki nawet w długich plikach.

Rozwiązany przykład

Załóżmy, że przeglądasz zmianę w tabeli użytkowników. Oto stan przed:

id,name,role,seats
7,Ada Lovelace,editor,3
8,Alan Turing,viewer,1

A oto stan po, wyeksportowany w innej kolejności wierszy:

id,name,role,seats
8,Alan Turing,viewer,1
7,Ada Lovelace,admin,5

Wrzuć je do surowego diffa wierszowego, a oba wiersze danych będą wyglądać na zmienione, bo zamieniły się pozycjami. Posortuj oba według kolumny id, a prawdziwa historia jest krótka:

Co naprawdę się zmieniło
Wiersz (wg id)KolumnaPrzedPoZmiana
7roleeditoradminZmodyfikowano
7seats35Zmodyfikowano
8Bez zmian (tylko przesunięto)

Jedna prawdziwa edycja: zmieniła się rola i liczba miejsc Ady. Wiersz Alana tylko się przesunął. Ten awans z editor na admin to dokładnie ten rodzaj rzeczy, którą chcesz wyłapać podczas przeglądu, a łatwo ją przeoczyć, gdy jest pogrzebana pod wierszami, które diff błędnie oznaczył jako zmienione.

Eliminowanie szumu kolejności wierszy w wierszu poleceń

Jeśli twoje pliki są już na dysku, a wiersze nie mają wewnętrznej kolejności, ten sam pomysł "najpierw posortuj" działa z dwoma krótkimi poleceniami. Zostaw nagłówek na miejscu i posortuj resztę:

(head -1 old.csv; tail -n +2 old.csv | sort) > old.sorted.csv
(head -1 new.csv; tail -n +2 new.csv | sort) > new.sorted.csv
diff old.sorted.csv new.sorted.csv

Teraz diff zgłasza tylko wiersze, które naprawdę się zmieniły, bo oba pliki są w tej samej kolejności. Przy porównaniach według klucza, które ignorują też kolejność kolumn, csvsort i csvjoin z csvkit dają więcej kontroli. To terminalowy odpowiednik sortowania obu stron przed porównaniem w przeglądarce.

Separatory, cudzysłowy i niechlujna rzeczywistość

Prawdziwe pliki CSV nieustannie łamią reguły. Pole zawierające przecinek musi być ujęte w cudzysłów, więc "Lovelace, Ada" to jedno pole, nie dwa. Cudzysłowy wewnątrz pola w cudzysłowie są podwajane: "Powiedziała ""cześć""". A sam separator bywa różny: arkusze kalkulacyjne w ustawieniach lokalnych z przecinkiem dziesiętnym eksportują ze średnikami, a pliki rozdzielane tabulatorami (TSV) są częste w potokach danych. Przed porównaniem upewnij się, że oba pliki używają tego samego separatora i tej samej konwencji cudzysłowów, albo znormalizuj je parserem zgodnym z RFC 4180. W przeciwnym razie diff porównuje dwa różne dialekty, a nie dwie wersje tych samych danych.

Typowe pułapki, na które warto uważać

PułapkaDlaczego boliRozwiązanie
Niezgodne separatoryPrzecinek vs. średnik sprawia, że każde pole wygląda inaczejNajpierw znormalizuj do jednego separatora
BOM na początkuUkryty znacznik kolejności bajtów zmienia pierwszą komórkę nagłówkaUsuń BOM przed porównaniem
ID z wiodącymi zeramiArkusz mógł zamienić 007 na 7Trzymaj kolumny ID jako tekst; porównuj jako ciągi znaków
Osadzone znaki nowej liniiPole w cudzysłowie może zawierać podział wiersza, przesuwając każdy kolejny wierszUżyj prawdziwego parsera CSV, a nie podziału na wiersze
Spacje na końcu w komórkachNiewidoczne spacje pokazują się jako zmianaPrzytnij wartości komórek przed porównaniem

Kiedy arkusz kalkulacyjny jest lepszym narzędziem

Diff tekstowy jest idealny do wskazania, które wiersze się zmieniły, i do przeglądania zmiany jako danych. Ale jeśli potrzebujesz filtrować, tworzyć tabele przestawne lub porównywać formułą przez tysiące wierszy, arkusz kalkulacyjny pasuje lepiej: zaimportuj oba pliki, wyrównaj je według klucza i użyj wyszukiwania, aby oznaczyć niezgodności. Te dwa podejścia się uzupełniają. Użyj diffa do szybkiego wizualnego odczytu, a arkusza, gdy musisz pokroić dane. W obu przypadkach po reguły formatu źródłowego sięgnij do przeglądu CSV w Wikipedii, to solidne źródło.

Powiązane narzędzia

CSV rzadko jest jedynym formatem, z którym masz do czynienia. Jeśli te same dane istnieją także jako JSON, porównanie JSON stosuje ten sam pomysł. Usuwanie duplikatów w kolumnie wartości jest szybkie z usuwaniem zduplikowanych wierszy, a ustawienie wierszy w przewidywalnej kolejności przed diffem to dokładnie to, do czego służy sortowanie wierszy.

Najczęściej zadawane pytania

Czy porównywanie plików CSV online przesyła je gdziekolwiek?
Na comparetext.org diff działa w twojej przeglądarce. Dwa pliki CSV są porównywane przez JavaScript na twoim własnym komputerze, więc nic nie jest wysyłane na serwer, dopóki wyraźnie nie klikniesz Zapisz lub Udostępnij. Dzięki temu jest bezpieczny dla eksportów klientów, danych finansowych i innych arkuszy, których nie chciałbyś wklejać na stronie wysyłającej dane przy każdym naciśnięciu klawisza.
Dlaczego moje dwa pliki CSV pokazują każdy wiersz jako różny?
Prawie zawsze chodzi o kolejność wierszy lub separator, a nie prawdziwe zmiany. Jeden eksport jest posortowany inaczej niż drugi, albo jeden używa przecinków, a drugi średników, albo różnią się znaki końca wiersza. Upewnij się, że oba pliki używają tego samego separatora, a następnie posortuj oba według kolumny klucza, by kolejność przestała mieć znaczenie. Potem diff zwykle kurczy się do garstki wierszy i komórek, które naprawdę się zmieniły.
Jak porównać dwa pliki CSV, ignorując kolejność wierszy?
Przed porównaniem posortuj oba pliki według stabilnej kolumny klucza. Jeśli wiersze mają ID, sortuj według niego; w przeciwnym razie posortuj cały wiersz. Zostaw wiersz nagłówka na miejscu i sortuj tylko wiersze danych. W przeglądarce możesz wkleić posortowane wersje; w wierszu poleceń posortuj plik po nagłówku. Gdy oba pliki są w tej samej kolejności, w diffie pojawiają się tylko wiersze, które faktycznie się zmieniły, zamiast każdego wiersza, który po prostu się przesunął.
Dlaczego mój CSV używa średników zamiast przecinków?
Wiele europejskich ustawień lokalnych używa przecinka jako separatora dziesiętnego, więc aplikacje arkuszy kalkulacyjnych eksportują CSV ze średnikiem jako separatorem, aby uniknąć niejednoznaczności. Dane są te same; różni się tylko separator. Przed porównaniem dwóch plików upewnij się, że używają tego samego separatora, inaczej zobaczysz każde pole oznaczone jako zmienione. Znormalizowanie obu do przecinków (lub obu do średników) narzędziem rozumiejącym CSV to naprawia. Pliki rozdzielane tabulatorami mają ten sam problem z innym separatorem.
Jak porównać pliki CSV o różnej kolejności kolumn?
Zwykły diff tekstowy porównuje wiersze od lewej do prawej, więc przestawione kolumny wyglądają na całkowitą zmianę, nawet gdy dane się zgadzają. Aby sobie z tym poradzić, najpierw przestaw kolumny tak, by pasowały w obu plikach, albo użyj narzędzia rozumiejącego CSV, które porównuje według nazwy nagłówka, a nie pozycji. Narzędzia wiersza poleceń, takie jak csvkit, potrafią wybierać i przestawiać kolumny po nazwie. Gdy kolumny ustawią się w tej samej kolejności, zwykły diff wiersz po wierszu znów działa.
Czy mogę porównać duże pliki CSV bez zawieszania strony?
Tak, do pewnego stopnia. Diff w trybie wierszowym pozostaje szybki przy plikach z tysiącami wierszy, bo najpierw porównuje całe wiersze, a nie każdy znak. Bardzo duże pliki (dziesiątki megabajtów lub miliony wierszy) lepiej obsłużyć narzędziem wiersza poleceń, takim jak csvkit, lub importem do bazy danych, które strumieniują dane. Dla eksportu, przez który da się wygodnie przewinąć w przeglądarce, diff online to szybsza opcja.

Gotowy, by spróbować? Wklej swoje pliki do narzędzia do porównywania CSV i zobacz, co się zmieniło.