Как отсортировать этот CSV-файл по дате с помощью команды сортировки Unix? - PullRequest
1 голос
/ 20 мая 2019

Я никогда не использовал UNIX раньше, и я использую это, потому что я не смог найти решение для Windows, чтобы отсортировать этот список по дате для такого большого файла.

Я пытаюсь отсортировать файл CSV с14 миллионов записей (файл 2 гига).Файл содержит все транзакции такси, которые произошли в 2013 году в январе месяце.Я хотел отсортировать список по дате, чтобы выбрать только данные за первую неделю.

Я нашел https://www.gnu.org/software/coreutils/manual/html_node/sort-invocation.html и пытался написать команду, которая будет делать то, что я хочу.До сих пор я пробовал

sort -t, -k 6n 8-trip_data_1.csv

, который не работал.

Я думаю, я хочу сказать, чтобы он сортировал по 6-му столбцу (время получения даты), а затем по 910 индексов этого столбца, потому что это все, что будет меняться в столбце данных в файле.Я положил некоторые из таблицы ниже.

medallion,hack_license,vendor_id,rate_code,store_and_fwd_flag,pickup_datetime,dropoff_datetime,passenger_count,trip_time_in_secs,trip_distance,pickup_longitude,pickup_latitude,dropoff_longitude,dropoff_latitude
A6699B6310BFDF8D1EE42C12622D94FA,66C6E65E8D6476B8DDA075A01D63E78A,VTS,1,,2013-01-16 19:21:00,2013-01-16 19:35:00,2,840,1.71,-73.986603,40.739986,-73.99221,40.719715
B45D26A20BE724B0F752461C624233CB,B240D08915F9F593F219D9109127FF1A,VTS,1,,2013-01-16 19:26:00,2013-01-16 19:32:00,3,360,.67,-73.982338,40.768349,-73.981285,40.774017

Ответы [ 2 ]

1 голос
/ 20 мая 2019

Вам не нужно n - действительно, это контрпродуктивно. Даты представлены в формате ISO 8601 и сортируются по порядку времени при алфавитно-цифровой сортировке. Числовая сортировка обращает внимание только на часть поля 2013 года; остальное не является частью единого числа. Вам также не нужно беспокоиться о подмножестве информации о времени - тот факт, что меняются только некоторые детали, не имеет значения.

Вы дали очень минимальный набор данных с информацией о времени получения уже в отсортированном порядке, поэтому нам нужно немного изобретательнее. Информация о заголовке не будет сортироваться численно; Вы можете удалить это, или позволить этому плавать вокруг. Чтобы показать, что сортировка работает при сортировке данных, я указываю r (обратный порядок). Это помещает данные заголовка вверху и переворачивает две строки фактических данных.

$ sort -t, -k6r data.file
medallion,hack_license,vendor_id,rate_code,store_and_fwd_flag,pickup_datetime,dropoff_datetime,passenger_count,trip_time_in_secs,trip_distance,pickup_longitude,pickup_latitude,dropoff_longitude,dropoff_latitude
B45D26A20BE724B0F752461C624233CB,B240D08915F9F593F219D9109127FF1A,VTS,1,,2013-01-16 19:26:00,2013-01-16 19:32:00,3,360,.67,-73.982338,40.768349,-73.981285,40.774017
A6699B6310BFDF8D1EE42C12622D94FA,66C6E65E8D6476B8DDA075A01D63E78A,VTS,1,,2013-01-16 19:21:00,2013-01-16 19:35:00,2,840,1.71,-73.986603,40.739986,-73.99221,40.719715
$

Или в порядке возрастания (заголовок идет в конце):

$ sort -t, -k6 data.file
A6699B6310BFDF8D1EE42C12622D94FA,66C6E65E8D6476B8DDA075A01D63E78A,VTS,1,,2013-01-16 19:21:00,2013-01-16 19:35:00,2,840,1.71,-73.986603,40.739986,-73.99221,40.719715
B45D26A20BE724B0F752461C624233CB,B240D08915F9F593F219D9109127FF1A,VTS,1,,2013-01-16 19:26:00,2013-01-16 19:32:00,3,360,.67,-73.982338,40.768349,-73.981285,40.774017
medallion,hack_license,vendor_id,rate_code,store_and_fwd_flag,pickup_datetime,dropoff_datetime,passenger_count,trip_time_in_secs,trip_distance,pickup_longitude,pickup_latitude,dropoff_longitude,dropoff_latitude
$

Кроме того, вы можете решить, какие даты являются релевантными, и изменить эту команду grep, чтобы выбрать правильные даты для первой недели, что уменьшает размер данных примерно до одной четверти от исходного размера.

grep ',2013-01-0[1-7] [0-2][0-9]:[0-5][0-9]:[0-5][0-9],' data.file

Это ищет даты в диапазоне с 2013-01-01 по 2013-01-07 (с учетом любого времени для каждого дня). Вы можете опустить регулярное выражение после пробела, если хотите; если данные действительны, это не будет иметь никакого значения, но регулярное выражение избегает выбора некоторых неверных данных. Очевидно, что вы можете изменить даты, если хотите, чтобы проходила первая неделя, например, с первого воскресенья по первую субботу (с 6-го по воскресенье по 12-е в субботу 2013 года):

grep -E ',2013-01-(0[6-9]|1[012]) [0-2][0-9]:[0-5][0-9]:[0-5][0-9],' data.file

Затем вы можете запустить этот сокращенный набор данных в процессе сортировки.

В будущем, пожалуйста, дайте примерно 5 строк для образцов данных - проще продемонстрировать, что работает, а что нет.

0 голосов
/ 20 мая 2019

Я уверен, что вы не хотите удалять заголовок и не хотите, чтобы он "плавал", поэтому создайте исполняемый файл sort_csv:

#!/usr/bin/perl

use strict;

sub my_cmp($$)
{
    my $a = shift;
    my $b = shift;
    return substr($a, 81, 8) cmp substr($b, 81, 8); # assuming seconds are always zero
}

print scalar (<>);
print sort my_cmp <>;

А затем:

# Make it executable
chmod +x sort_csv

sort_csv <input.csv >sorted.csv
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...