Jeśli mam plik csv, czy istnieje szybki sposób na wydrukowanie zawartości tylko jednej kolumny? Można bezpiecznie założyć, że każdy wiersz ma taką samą liczbę kolumn, ale zawartość każdej kolumny miałaby inną długość.
111
Możesz do tego użyć awk. Zmień „$ 2” na n-tą kolumnę, którą chcesz.
awk -F "\"*,\"*" '{print $2}' textfile.csv
echo '1,"2,3,4,5",6' | awk -F "\"*,\"*" '{print $2}'
drukuje2
zamiast2,3,4,5
.gawk -F"|" "{print $13}" files*.csv
...,"string,string",...
"
a ostatnia zakończy"
awk -F "\"*;\"*" '{print $2}' textfile.csv
tak.
cat mycsv.csv | cut -d ',' -f3
wydrukuje trzecią kolumnę.źródło
awk
Najprostszym sposobem, w jaki udało mi się to zrobić, było użycie csvtool . Miałem również inne przypadki użycia, aby użyć csvtool i może odpowiednio obsługiwać cudzysłowy lub ograniczniki, jeśli pojawiają się w samych danych kolumny.
Zastąpienie 2 numerem kolumny skutecznie wyodrębni dane kolumny, której szukasz.
źródło
cat input.csv | csvtool formath '%(2)\n' -
Uwaga Wiem, że cat tutaj jest bezużyteczny, ale podporządkuj go dla dowolnego polecenia, które normalnie wyeksportowałoby csv.format '%(2)\n'
polecenie nie mogło powiedzieć, gdzie kończy się jedno pole. (csvtool 1.4.2)csvtool
wydają się wymagać użycia-
jako nazwy pliku wejściowego do odczytu ze standardowego wejścia.csvtool format '%(1),%(10)\n' - < in.csv > out.csv
Wylądowałem tutaj, szukając wyodrębnienia z pliku rozdzielonego tabulatorami. Pomyślałem, że dodam.
Gdzie
-f2
wyodrębnia 2, niezerową kolumnę indeksowaną lub drugą kolumnę.źródło
cat
jest niepotrzebny:< textfile.tsv cut -f2 -s
Wiele odpowiedzi na te pytania jest świetnych, a niektórzy nawet zajrzeli do narożnych przypadków. Chciałbym dodać prostą odpowiedź, która może być przydatna na co dzień ... gdzie najczęściej trafiasz do tych narożnych przypadków (np. Unikanie przecinków lub przecinków w cudzysłowie itp.).
Więc używając BEGIN (Wykonaj przed pobraniem danych wejściowych) możemy ustawić to pole na cokolwiek chcemy ...
Powyższy kod wydrukuje trzecią kolumnę w pliku csv.
źródło
Inne odpowiedzi działają dobrze, ale ponieważ poprosiłeś o rozwiązanie przy użyciu tylko powłoki bash, możesz to zrobić:
Następnie możesz wyciągnąć kolumny (pierwsze w tym przykładzie) w następujący sposób:
Tak więc dzieje się tutaj kilka rzeczy:
while IFS=,
- oznacza to użycie przecinka jako IFS (wewnętrznego separatora pól), którego używa powłoka, aby wiedzieć, co oddziela pola (bloki tekstu). Zatem powiedzenie IFS = jest jak powiedzenie „a, b” to to samo, co „a b” byłoby, gdyby IFS = „” (czyli jest tym, czym jest domyślnie).read -a csv_line;
- to znaczy czytaj w każdym wierszu, pojedynczo i stwórz tablicę, w której każdy element nazywa się „csv_line” i wyślij to do sekcji „do” naszej pętli whiledo echo "${csv_line[0]}";done < file
- teraz jesteśmy w fazie „do” i mówimy echo zerowego elementu tablicy „csv_line”. Ta akcja jest powtarzana w każdym wierszu pliku. Ta< file
część mówi po prostu pętli while, z której należy czytać. UWAGA: pamiętaj, że w bash tablice są indeksowane do 0, więc pierwsza kolumna jest zerowym elementem.Więc masz to, wyciągając kolumnę z CSV w powłoce. Inne rozwiązania są prawdopodobnie bardziej praktyczne, ale to jest czysty bash.
źródło
Możesz użyć GNU Awk, zobacz ten artykuł w przewodniku użytkownika . Jako ulepszenie rozwiązania przedstawionego w artykule (w czerwcu 2015 r.), Następujące polecenie gawk umożliwia stosowanie podwójnych cudzysłowów w polach z podwójnymi cudzysłowami; podwójny cudzysłów jest tam oznaczony dwoma kolejnymi podwójnymi cudzysłowami (""). Co więcej, pozwala to na puste pola, ale nawet to nie obsługuje pól wielowierszowych . Poniższy przykład wyświetla trzecią kolumnę (za pośrednictwem
c=3
) pliku textfile.csv:Zwróć uwagę na użycie
dos2unix
do konwersji możliwych podziałów linii w stylu DOS (CRLF tj. „\ R \ n”) i kodowania UTF-16 (ze znacznikiem kolejności bajtów) odpowiednio na „\ n” i UTF-8 (bez znaku kolejności bajtów). Standardowe pliki CSV używają CRLF jako podziału wiersza, zobacz Wikipedia .Jeśli dane wejściowe mogą zawierać pola wielowierszowe, możesz użyć następującego skryptu. Zwróć uwagę na użycie specjalnego ciągu do oddzielania rekordów w wynikach (ponieważ domyślny separator nowej linii może występować w rekordzie). Ponownie, poniższy przykład wyświetla trzecią kolumnę (za pośrednictwem
c=3
) pliku textfile.csv:Istnieje inne podejście do problemu. csvquote może wyświetlać zawartość pliku CSV zmodyfikowanego w taki sposób, że znaki specjalne w polu są przekształcane w taki sposób, że do wybrania określonej kolumny można użyć zwykłych narzędzi przetwarzania tekstu Unix. Na przykład poniższy kod zwraca trzecią kolumnę:
csvquote
może być używany do przetwarzania dowolnych dużych plików.źródło
Oto przykład pliku CSV z 2 kolumnami
Aby uzyskać pierwszą kolumnę, użyj:
f oznacza pole, a d oznacza ogranicznik
Uruchomienie powyższego polecenia spowoduje wyświetlenie następującego wyniku.
Wynik
Aby uzyskać tylko drugą kolumnę:
A oto wyjście wyjściowe
Inny przypadek użycia:
Twój plik wejściowy csv zawiera 10 kolumn, a chcesz mieć kolumny od 2 do 5 i kolumny 8, używając przecinka jako separatora ”.
cut używa -f (co oznacza „pola”) do określenia kolumn i -d (co oznacza „separator”) do określenia separatora. Musisz określić to drugie, ponieważ niektóre pliki mogą używać spacji, tabulatorów lub dwukropków do oddzielania kolumn.
cut to narzędzie poleceń, a oto kilka przykładów:
źródło
Potrzebowałem odpowiedniego parsowania CSV, a nie
cut
/awk
i modlitwy. Próbuję tego na komputerze Mac bezcsvtool
, ale komputery Mac są dostarczane z rubinem, więc możesz:źródło
Najpierw utworzymy podstawowy plik CSV
Następnie otrzymujemy pierwszą kolumnę
źródło
gdzie 2 to interesująca Cię kolumna
możesz też zrobić
zrobić wiele kolumn
źródło
Myślę, że najłatwiej jest użyć csvkit :
Pobiera drugą kolumnę:
csvcut -c 2 file.csv
Jednak istnieje również csvtool i prawdopodobnie wiele innych narzędzi csv bash:
sudo apt-get install csvtool
(dla systemów opartych na Debianie)Spowoduje to zwrócenie kolumny z pierwszym wierszem zawierającym „ID”.
csvtool namedcol ID csv_file.csv
To zwróci czwarty wiersz:
csvtool col 4 csv_file.csv
Jeśli chcesz usunąć wiersz nagłówka:
csvtool col 4 csv_file.csv | sed '1d'
źródło
Zastanawiam się, dlaczego żadna z dotychczasowych odpowiedzi nie wspominała o csvkit.
Dokumentacja csvkit
Używam go wyłącznie do zarządzania danymi csv i do tej pory nie znalazłem problemu, którego nie mógłbym rozwiązać za pomocą cvskit.
Aby wyodrębnić jedną lub więcej kolumn z pliku cvs, możesz użyć
csvcut
narzędzia, które jest częścią zestawu narzędzi. Aby wyodrębnić drugą kolumnę, użyj tego polecenia:Strona referencyjna csvcut
Jeśli ciągi w csv są cytowane, dodaj znak cudzysłowu z
q
opcją:Zainstaluj za pomocą
pip install csvkit
lubsudo apt install csvkit
.źródło
Nie możesz tego zrobić bez pełnego parsera CSV.
źródło
cut
liczy?Używam tego kodu od jakiegoś czasu, nie jest to „szybkie”, chyba że policzysz „wycinanie i wklejanie z przepełnienia stosu”.
Używa operatorów $ {##} i $ {%%} w pętli zamiast IFS. Wzywa „err” i „die” i obsługuje tylko przecinki, myślniki i kreski jako znaki SEP (to wszystko, czego potrzebowałem).
Przykład:
źródło
Możesz także użyć pętli while
źródło