найти и заменить несколько шаблонов в определенном столбце csv на sed - PullRequest
0 голосов
/ 18 мая 2018

У меня есть CSV-файл, как это:

2018-May-17 21:33:16,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
2018-May-17 21:34:15,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
2018-May-17 21:35:17,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19

Мне нужно преобразовать только первый столбец в формат YYYYMMDDHHmmss, например:

20180517213316,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213415,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213517,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19

Как мне добиться этого с помощью sed без изменения других столбцов?

Ответы [ 5 ]

0 голосов
/ 18 мая 2018

Это может работать для вас (GNU sed):

l="Jan01Feb02Mar03Apr04May05Jun06Jul07Aug08Sep09Oct10Nov11Dec12"
sed -r 's/$/\n'"$l"'/;s/^(....)-(...)-(..) (..):(..):(.*)\n.*\2(..).*/\1\7\3\4\5\6/' file

Добавить таблицу соответствия в конец каждой строки и, используя сопоставление с образцом, группирование и обратные ссылки, преобразовать первый столбец в требуемую спецификацию.

0 голосов
/ 18 мая 2018

Sed, один вкладыш:

$ cat file.csv | sed 's/^\([[:digit:]]*\)-\([^ ]*\)\(.*\)/\2-\1\3/g' | sed 's/\([^,]*\),\(.*\)/echo $(date -d "\1" +%Y%m%d%H%M%S ),\2/e'

Пояснение

  • Преобразовать% Y-% m-% d в% m-% d-%Формат Y для использования по дате -d
  • Используйте sed для замены только первого столбца.
  • Используйте команду даты -d для чтения ввода даты.
  • Использованиедата +% Y% m% d% H% M% S, чтобы напечатать вывод
0 голосов
/ 18 мая 2018

После awk может помочь вам в том же.

awk -F"," '
BEGIN{
   num=split("jan,feb,mar,apr,may,jun,jul,aug,sept,oct,nov,dec",array,",");
   for(i=1;i<=num;i++){
      month[array[i]]=sprintf("%02d",i)}
}
{
   split($1,a,"[- ]");
   a[2]=month[tolower(a[2])];
   $1=a[1] a[2] a[4];
   gsub(/:/,"",$1)
}
1' OFS=","   Input_file

Объяснение кода:

awk -F"," '                                                                ##Setting field separator as comma here or lines.
BEGIN{                                                                     ##Starting BEGIN section for awk here.
   num=split("jan,feb,mar,apr,may,jun,jul,aug,sept,oct,nov,dec",array,",");##Using split to create a month names array and its length is stored in num variable.
   for(i=1;i<=num;i++){                                                    ##Starting a for loop from variable value i=1 to till value of num here.
      month[array[i]]=sprintf("%02d",i)}                                   ##Creating an array month whose index is array value with index i and value is variable i.
}
{                                                                          ##Starting main section here which will be executed during Input_file reading by awk.
   split($1,a,"[- ]");                                                     ##Using split to split $1 into array a whose delimiter are space and - in that line.
   a[2]=month[tolower(a[2])];                                              ##Setting 2nd value of array a to value of month array, to get months into digit format.
   $1=a[1] a[2] a[4];                                                      ##Re-creating first field with values of first, second and third values of array a.
   gsub(/:/,"",$1)                                                         ##globally substituting colon with NULL in first colon.
}
1                                                                          ##Using 1 here to print the current line.
' OFS="," Input_file                                                    ##Setting output field separator as comma and mentioning Input_file name here.
0 голосов
/ 18 мая 2018
awk -F, '{ gsub(/:| /, "", $1); 
    x=(match("JanFebMarAprMayJunJulAugSepOctNovDec", substr($1,6,3))+2)/3;
    x=x>9?x:0x; gsub(/-.*-/, x, $1) }1' OFS=, infile

Выход:

20180517213316,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213415,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213517,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19

Как это работает

  • this -F, определяет, какой разделитель является разделенными полями.
  • this gsub(/:| /, "", $1) удаляет пробелы и двоеточия из первого поля.
  • this substr($1,6,3) возвращает название месяца из первого поля
  • this match("JanFebMarAprMayJunJulAugSepOctNovDec", substr($1,6,3)) возвращает первую позицию символа (индекс) названия месяца начинается со строки всех названий месяцев JanFebMarAprMayJunJulAugSepOctNovDec = 13 . результат этого match(...) всегда будет одним из этих 1, 4, 7, 10, 13, 16, 19, 22, 25, 28, 31, 34 ; теперь мы получили 13 , и поскольку каждое имя месяца имеет длину 3 , мы должны найти способ вернуть 5 в результате, чтобы мы добавили 2 к результату, чтобы указать позицию в конце соответствующего названия месяца , а затем разделить на 3 13+2/3=5.
  • это x=x>9?x:0x с добавлением 0 к указанному выше числу, если оно меньше 10
  • this gsub(/-.*-/, x, $1) заменяет совпадение между дефисами, которое является названием месяца значением x только в первом поле.
  • это 1 всегда истинное условие и приводит к выводу строки awk read
  • это OFS=, устанавливает O utput F eild S eperator обратно на запятую ,.
0 голосов
/ 18 мая 2018

Есть два способа сделать замену.Но обоим из этих двух способов необходим скрипт оболочки справки .

версия PHP

sed -r 's/([^,]*),(.*)/echo $(echo "\1"|.\/php.sh),\2/e' file

php.sh

#!/bin/sh

read str
php -r "echo date('YmdHis', strtotime('$str'));"

версия bash

sed -r 's/([^-]*)-([^-]*)-([0-9]{1,2})[[:space:]]*([0-9]{1,2}):([0-9]{1,2}):([0-9]{1,2}),(.*)/echo \1$(echo "\2"\|.\/help.sh)\3\4\5\6,\7/e' file

help.sh

#!/bin/sh

read str

case $str in
    Jan) MON=01 ;;
    Feb) MON=02 ;;
    Mar) MON=03 ;;
    Apr) MON=04 ;;
    May) MON=05 ;;
    Jun) MON=06 ;;
    Jul) MON=07 ;;
    Aug) MON=08 ;;
    Sep) MON=09 ;;
    Oct) MON=10 ;;
    Nov) MON=11 ;;
    Dec) MON=12 ;;
esac

echo $MON

Вывод:

20180517213316,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213415,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19
20180517213517,VF-AUDI-prod,Start:2018-May-17:End:2018-May-19

Для получения дополнительной информации об использовании echo, встроенного в sed, вы можете перейти по этой ссылке

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