|
перевод даты в юникс секунды, нужен код на си |
|
|
|
 |
Ответов
(1 - 13)
|
Aug 24 2015, 09:18
|
Частый гость
 
Группа: Свой
Сообщений: 124
Регистрация: 27-05-05
Из: St.-P
Пользователь №: 5 462

|
Цитата(super_puper @ Aug 23 2015, 22:57)  думал это очень распространено но потратил 2 часа не нашел кода на си для такой типичной операции.
формат: год месяц день минуты секунды перевести в секунды с 1970 года
желательно проверенный красивый код и наверное без циклов) Не оно? mktime
|
|
|
|
|
Aug 24 2015, 19:37
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
QUOTE (super_puper @ Aug 24 2015, 11:57)  думал это очень распространено но потратил 2 часа не нашел кода на си для такой типичной операции. Уже и школьная арифметика не по зубам  , а так-бы потратили 15 минут и написали: CODE year -= 1970; leaps = (year+2)/4; if( !( (year+70) & 3 )&&( month < 3) ) --leaps; days = year*365 + leaps + monthday[month-1] + (day-1); utime = days*(24*60*60) + (hour+timezone)*(60*60) + min*60 + sec; Это если на голом месте, а так вообще сишная time()
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
Aug 25 2015, 05:30
|
Местный
  
Группа: Участник
Сообщений: 222
Регистрация: 14-12-12
Из: новосибирск
Пользователь №: 74 845

|
Цитата(zltigo @ Aug 25 2015, 01:37)  Уже и школьная арифметика не по зубам  , а так-бы потратили 15 минут и написали: Код year -= 1970; leaps = (year+2)/4; if( !( (year+70) & 3 )&&( month < 3) ) --leaps; days = year*365 + leaps + monthday[month-1] + (day-1); utime = days*(24*60*60) + (hour+timezone)*(60*60) + min*60 + sec; Это если на голом месте, а так вообще сишная time()  както кусок кода не полный помоему -- monthday[month-1]??
Сообщение отредактировал super_puper - Aug 25 2015, 05:30
|
|
|
|
|
Aug 25 2015, 06:38
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
QUOTE (super_puper @ Aug 25 2015, 08:30)  както кусок кода не полный помоему -- monthday[month-1]?? А Вы даже не догадываетсь, что это такое  Это таблица количества дней в месяце. Ну хоть ее из календаря заполнили-бы. CODE 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334 QUOTE (esaulenka @ Aug 25 2015, 09:17)  Это называется "велосипедостроение". Бессмысленное и беспощадное. Как назвать Ваши две реплики я не буду развернуто характиризовать из вежливости. Но, 1) послать, как Вы сделали, в википедию совсем ума не надо. 2) даже помянутая мной сишная функция time() она вообще-то системозависимая - нет операционки с часами реального времени, нет и волшебной функции. Можно, конечно, через две других с заполнением промежуточных структур преобразоваться. Но и самому под голый контроллер написать несложно. И не надо заниматься часами поисками готовых "велосипедных библиотек" соразмерных поискам "чернил для третьего класса". Ну и ЕДИНОЖДЫ написав что-то полезное Вы сможете им пользоваться и в дальнейшем.
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
Aug 25 2015, 07:15
|
Гуру
     
Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713

|
Цитата(super_puper @ Aug 24 2015, 14:57)  думал это очень распространено но потратил 2 часа не нашел кода на си для такой типичной операции. Для операции "/=" тоже примеры кода в инете ищете? Функция Encode() преобразует дату в секунды с любым базовым годом, не обязательно 1970: CODE #define BASE_YEAR 2011 //базовый год Службы времени #define N_YEARS 136 //кол-во лет, охватываемых Службой времени //(служба времени работоспособна от BASE_YEAR года до (BASE_YEAR+N_YEARS-1) года включительно)
u8 const month2days[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
struct DateTime { u8 seconds, minutes, hours, date, month, day; u16 year; u32 Encode() const; int Set(u32); };
//кол-во дней перед началом года 'y' #define daysBeforeYear(y) ((u32)((y) - 1) * 365 + \ (u32)((y) - 1) / 4 - (u32)((y) - 1) / 100 + (u32)((y) - 1) / 400)
//кол-во дней, охватываемых Службой времени (макс. диапазон времени в днях) #define N_DAYS (daysBeforeYear(BASE_YEAR+N_YEARS) - daysBeforeYear(BASE_YEAR))
//возвращает true - если год невисокосный, false - иначе u32 isNoVisokos(u32 year) { u32 c, i; if (!(c = (i = year) & 3)) if ((i /= 100) * 100 == year) c = i & 3; return c; }
//преобразует DateTime в кол-во секунд от начала BASE_YEAR //при ошибке возвращает ~0 //член day - игнорируется u32 DateTime::Encode() const { u32 cc, i, j; u8 const *s; if ((cc = year) - BASE_YEAR >= N_YEARS) return ~0; j = daysBeforeYear(cc) - daysBeforeYear(BASE_YEAR); if ((i = month) > 11) return ~0; s = month2days; while ((s32)--i >= 0) j += *s++; i = *s; if (!isNoVisokos(cc)) { if ((uint)month > 1) j++; if (month == 1) i++; } if (date >= i) return ~0; j = (date + j) * 24; if ((uint)hours > 23) return ~0; j = (hours + j) * 60; if ((uint)minutes > 59) return ~0; j = (minutes + j) * 60; if ((uint)seconds > 59) return ~0; return seconds + j; }
|
|
|
|
|
Aug 25 2015, 07:49
|

Профессионал
    
Группа: Свой
Сообщений: 1 032
Регистрация: 13-03-08
Из: Маськва
Пользователь №: 35 877

|
Цитата(zltigo @ Aug 25 2015, 09:38)  1) послать, как Вы сделали, в википедию совсем ума не надо. Тем не менее, там есть готовый кусок кода. Работающий. А написать своё, тесты продумать-сделать-прогнать... У меня часа два займёт. Можно только восхищаться человеком, производительность которого на порядок выше. Я сам не большой любитель супербиблиотек со встроенной кофеваркой. Но тут задача - стандартнее придумать сложно, надо брать готовое.
--------------------
Тут обсуждается творческий порыв, а не соответствие каким-либо стандартам ©
|
|
|
|
|
Aug 25 2015, 08:17
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
QUOTE (esaulenka @ Aug 25 2015, 10:49)  Тем не менее, там есть готовый кусок кода. Работающий. Да, не заметил под спойлером  . Хотя, конечно, "кусок кода" еще тот по замороченности на ровном месте, да и писанный под определенное окружение. Тот кусок, котрый я привел, писал, не поверите  - в доинтернетовскую эпоху - CCCР был, а интернета не было  . Просто взял и написал - задача ведь банально-арифметическая. И с тех пор беру его у себя-же и не ищу кто-бы его "изобрел".
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
Aug 25 2015, 08:44
|
Гуру
     
Группа: Свой
Сообщений: 2 724
Регистрация: 14-05-07
Из: Ярославль, Россия
Пользователь №: 27 702

|
Цитата(super_puper @ Aug 24 2015, 11:57)  думал это очень распространено но потратил 2 часа не нашел кода на си для такой типичной операции.
формат: год месяц день минуты секунды перевести в секунды с 1970 года
желательно проверенный красивый код и наверное без циклов) Перевод туда-сюда. Правда, начало эпохи 01.01.2000 00:00:00. Коректно работет до 2100 года. Время добавить самостоятельно) CODE //----------------------------------------------------------------------------- // void int_to_date(const DWORD jd, DWORD *y, DWORD *m, DWORD *d) //----------------------------------------------------------------------------- void int_to_date(const DWORD jd, DWORD *y, DWORD *m, DWORD *d) { int aa, bb, cc, dd, ee, mm, xx;
aa = jd + 2483589; bb = (aa * 4 + 3) / 146097; cc = aa - ((146097 * bb) >> 2); dd = (4 * cc + 3) / 1461; ee = cc - ((1461 * dd) >> 2); mm = ((5 * ee + 2) * 13707) >> 21;
*d = ee - ((16043274 * mm + 209716) >> 19) + 1; *m = mm + 3 - 12 * ((mm * 27) >> 8); *y = 100 * bb + dd - 4800 + ((mm * 27) >> 8); }
//----------------------------------------------------------------------------- // DWORD date_to_int(DWORD y, DWORD m, const DWORD d) //----------------------------------------------------------------------------- DWORD date_to_int(DWORD y, DWORD m, const DWORD d) { if(m < 3) { m += 12; y -= 1; } return ((y * 1461) >> 2) + ((m * 306 + 7) / 10) + d - 730533; }
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|