LINUX.ORG.RU

Более совместимый вариант:

[code] date -d '1970-01-01 UTC 1298383557 seconds' [/code]

botkin
()
Ответ на: комментарий от madgnu

Не хочу заводить похожую тему, поэтому попробую спросить тут.
Как перевести в unixtime дату в виде 20110223122334 (это +%Y%m%d%H%M%S)?
Конечно если руками переформатировать в вид 2011-02-23 12:23:34 работать будет, но есть необходимость в модификации и пересчёте даты в нескольких тысячах строк.
Подозреваю можно через set задать в системе дату в таком формате сначала, но на сервере баловство с установкой даты чревато

zolden ★★★★★
()
Ответ на: комментарий от adriano32

Ну, честно говоря, замена даты лишь одна часть проблемы.
Дело в том, что это очень большой файл с разделителями, дата в 11м поле.
Дата неправильная и мне надо её исправлять на правильную (текущее значение + смещение в секундах для поправки)
Для этого и собирался переводить в unixtime, прибавлять смещение, потом переводить обратно).
Я про sed уже тоже думал (и про awk), но ничего толкового не придумал.
Пример записи (дата - 20110221220506):

934,5,,130:49.2,29,094,,,,,20110221220506,20,0,,B130,,3751,,302,760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,3F:1|348,8.209,,,,,,,,,,,,

zolden ★★★★★
()
Ответ на: комментарий от zolden

Мой воспалённый мозг родил такую конструкцию, обходящуюся лишь bash и sed и tr
1. Насколько я понял, файл идёт в одну строку, записи разделены вертикальной чертой. Расположим для удобства каждую запись в отдельной строке, предварительно убрав последнюю вертикальную черту в изначальном файле во избежание пустой строки в конце всех последующих файлов:

$ sed "s/|/\\`echo -e '\n\ '`/g" initial_file | sed -e "s/^\ //g" > every_record_in_separted_line_file
Простите за костыль с пробелом, просто \n не сработало.

2. Делим файл на три части-колонки: до даты, саму дату, после даты
$ sed "s/[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*$//g" every_record_in_separted_line_file > first_column_file
$ sed "s/\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*$//g" every_record_in_separted_line_file | sed "s/^[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,//g" > second_column_file
$ sed "s/^[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[^\,]*\,[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]//g" every_record_in_separted_line_file > third_column_file
3. Делаем из второй колонки скрипт для преобразования в unix epoch time (можно сразу с корректировкой, но у меня с ходу получилось только добавить +second +minute +hour итп, но несколько, например, +4second, не получилось, добавило зону)
$ sed "s/^[0-9][0-9][0-9][0-9]/&\-/g" second_column_file | sed "s/^[0-9][0-9][0-9][0-9]\-[0-9][0-9]/&\-/g" | sed "s/^[0-9][0-9][0-9][0-9]\-[0-9][0-9]\-[0-9][0-9]/&\ /g" | sed "s/^[0-9][0-9][0-9][0-9]\-[0-9][0-9]\-[0-9][0-9]\ [0-9][0-9]/&\:/g" | sed "s/^[0-9][0-9][0-9][0-9]\-[0-9][0-9]\-[0-9][0-9]\ [0-9][0-9]\:[0-9][0-9]/&\:/g" | sed "s/^/date\ \-\-date\=\'/g" | sed "s/$/\'\ \+\%s/g" > convert_date_script
Не знаю насколько большой у вас файл, если большой, то на пайпах может захлебнуться и придётся разбивать на отдельные операции с выхлопом во временный файл.
Конвертируем даты в epoch time
$ sh convert_date_script > second_column_file_in_unix_epoch
4. Выполняем коректировку времени (там добавление секунд что ли)
$ sed "s/^/echo\ \$\(\(/g" second_column_file_in_unix_epoch | sed "s/$/\+87\)\)/g" > date_addition_script
$ sh date_addition_script > second_column_file_added_unix_epoch
6. Преобразовываем в родной формат
$ sed "s/^/date\ \-\-date\=\"\@/g" second_column_file_added_unix_epoch | sed "s/$/\"\ \+\%Y\%m\%d\%H\%M\%S/g" > convert_to_old_format_script
$ sh convert_to_old_format_script > second_column_file_added
7. Теперь сливаем всё обратно вместе
$ paste -d "" first_column_file second_column_file_added third_column_file > output_file
8. Преобразуем в одну строку с разделением вертикальной чертой
$ cat output_file | tr "\n" "|" > final_output_file

Проверил, работает.

Готов посыпать пеплом голову, услышав более элегантный вариант. Не стесняйтесь, тролльте.

adriano32 ★★★
()
Ответ на: комментарий от adriano32

Вы мой герой, раз смогли сделать такое - выглядит потрясно.
Но вы меня простите, так как я вас ввёл в заблуждение (совершенно без злого умысла).
Разделители тут всё-таки - запятые.
Всего порядка 74х полей.
Пайп ближе к концу - это законный символ одного из полей.
Плюс, почему я не смог сделать этого седом в лоб - поля могут быть переменной длины и даже пустые.
Объём - сотни мегабайт. Вот трёхстрочный пример.

934,5,,130:43.2,29,094,,,,,20110221220506,20,0,,B130,,3751,,302,760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,3F:1|348,8.209,,,,,,,,,,,,
934,5,,230:419.2,29,094,,,,,20110221221512,320,0,,B30,,37513,,345,7160,type2,,0dd,B13,,,,,,,1,,1,,,20,,,,3F:1|348,8.4209,,,,,,,,,,,,
23,5,,130:149.2,29,094,,,,,20110221222126,20,0,,B10,,23751,,3012,2760,type25,,0d3,B1,,,,,,,1,,1,,,20,,,,3FA:1|348,8.2039,,,,,,,,,,,,
934,5,,130:49.2,29,094,,,,,20110221240214,20,0,,B130,,37351,,130,5760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,DD3F:1|348,328.209,,,,,,,,,,,,

zolden ★★★★★
()
Ответ на: комментарий от zolden

Может я что-то недопонял, что что мешает взять любой скриптовый язык,
* Отсплитить строку в массив по разделителям.
* Перевести одиннадцатое поле в unixtime, прибавить поправку и перевести обратно.
* Заджойнить массив в строку.
* Повторять до конца файла.

geekless ★★
()
Ответ на: комментарий от zolden

А, ну тогда без первого пункта, раз вертикальная черта-законный символ.
\,[^\,]* соответствует запятая и потом блок из нуля и более любых символов кроме самой запятой, это заменяет что ,,, что ,5

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

adriano32 ★★★
()
Ответ на: комментарий от geekless

Отсплитить мне ничего не мешает. Мой первый вопрос как раз и был про нормальный способ перевести время моём текущем формате в unixtime, вы видимо его прокрутили.

zolden ★★★★★
()
Ответ на: комментарий от adriano32

Ок, теперь понял. Дальше думаю разберусь. Большое спасибо!

zolden ★★★★★
()
Ответ на: комментарий от zolden

Мой первый вопрос как раз и был про нормальный способ перевести время моём текущем формате в unixtime, вы видимо его прокрутили.

Странный вопрос. man strptime strftime. Штатные средства для работы с датами есть в любом языке.

$ ruby 123.rb < 123.data 
934,5,,130:43.2,29,094,,,,,20110221220506,20,0,,B130,,3751,,302,760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,3F:1|348,8.209,,,,,,,,,,,,
934,5,,130:43.2,29,094,,,,,20110221220556,20,0,,B130,,3751,,302,760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,3F:1|348,8.209
934,5,,230:419.2,29,094,,,,,20110221221512,320,0,,B30,,37513,,345,7160,type2,,0dd,B13,,,,,,,1,,1,,,20,,,,3F:1|348,8.4209,,,,,,,,,,,,
934,5,,230:419.2,29,094,,,,,20110221221602,320,0,,B30,,37513,,345,7160,type2,,0dd,B13,,,,,,,1,,1,,,20,,,,3F:1|348,8.4209
23,5,,130:149.2,29,094,,,,,20110221222126,20,0,,B10,,23751,,3012,2760,type25,,0d3,B1,,,,,,,1,,1,,,20,,,,3FA:1|348,8.2039,,,,,,,,,,,,
23,5,,130:149.2,29,094,,,,,20110221222216,20,0,,B10,,23751,,3012,2760,type25,,0d3,B1,,,,,,,1,,1,,,20,,,,3FA:1|348,8.2039
934,5,,130:49.2,29,094,,,,,20110221230214,20,0,,B130,,37351,,130,5760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,DD3F:1|348,328.209,,,,,,,,,,,,
934,5,,130:49.2,29,094,,,,,20110221230304,20,0,,B130,,37351,,130,5760,type2,,0dd,B1,,,,,,,1,,1,,,20,,,,DD3F:1|348,328.209
$ cat 123.rb 
require 'date'
f = '%Y%m%d%H%M%S'
offset = 50
STDIN.read.each_line do |line|
	puts line
	a = line.strip.split(',')
	a[10] = (DateTime.strptime(a[10], f).to_time + offset).utc.strftime(f)
	puts a.join(',')
end
geekless ★★
()
Ответ на: комментарий от geekless

Спасибо за наводочку. Уж было порадовался что можно будет переписать на awk, но к удивлению обнаружил там только strftime. Ф-ции strptime там почему-то нет

zolden ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.