5.3. Выполнение вычислений с датами и временем
5.3. Выполнение вычислений с датами и временем
Проблема
Требуется узнать количество времени, прошедшего между двумя точками даты/времени.
Решение
Если обе временные точки находятся между 1970 и 2038 годами, то используйте тип time_t и функцию difftime, определенную в заголовочном файле <ctime>. Пример 5.6 показывает, как вычислить число дней, прошедших между двумя датами.
Пример 5.6. Вычисление даты и времени в формате time_t
#include <ctime>
#include <iostream>
#include <cstdlib>
using namespace std;
time_t dateToTimeT(int month, int day, int year) {
// 5 января 2000 года передается как (1, 5, 2000)
tm tmp = tm();
tmp.tm_mday = day;
tmp.tm_mon = month - 1;
tmp.tm_year = year - 1900;
return mktime(&tmp);
}
time_t badTime() {
return time_t(-1);
}
time_t now() {
return time(0);
}
int main() {
time_t date1 = dateToTimeT(1,1,2000);
time_t date2 = dateToTimeT(1,1,2001);
if ((date1 == badTime()) || (date2 == badTime())) {
cerr << "невозможно создать структуру time_t" << endl;
return EXIT_FAILURE;
}
double sec = difftime(date2, date1);
long days = static_cast<long>(sec / (60 * 60 — 24));
cout << число дней между 1 января 2000 г. и 1 января 2001 г. составляет ";
cout << days << endl;
return EXIT_SUCCESS;
}
Программа из примера 5.6 должна вывести:
число дней между 1 января 2000 г. и 1 января 2001 г. составляет 366
Обратите внимание, что 2000 год високосный, так как, несмотря на то что он делится на 100, он также делится и на 400 и, следовательно, состоит из 366 дней.
Обсуждение
Тип time_t — это зависящий от реализации арифметический тип. Это означает, что это либо целый тип, либо тип с плавающей точкой, и, таким образом, он поддерживает основные арифметические операции. Его можно складывать, вычитать, делить, умножать и т.д. Чтобы вычислить интервал между двумя значениями time_t в секундах, используйте функцию difftime. Не думайте, что сам time_t содержит секунды, даже если это и так. Многие реализации C++ могут в ближайшем будущем молча изменить его так, чтобы он содержал доли секунд (это одна из причин, по которым difftime возвращает double).
Если ограничения time_t слишком жестки, то вместо него для вычисления временных интервалов потребуется использовать различные классы из библиотеки Boost date_time. Пример 5.7 показывает, как использовать классы Boost для вычисления числа дней в 20-м и 21-м столетиях.
Пример 5.7. Вычисление даты и времени с помощью date_duration
#include <iostream>
#include <boost/date_time/gregorian/gregorian.hpp>
using namespace std;
using namespace boost::gregorian;
int main() {
date_duration dd = date(2000, 1, 1) - date(1900, 1, 1);
cout << "Двадцатый век содержал " << dd.days() << " дней" << endl;
dd = date(2100, 1, 1) - date(2000, 1, 1);
cout << "Двадцать первый век будет содержать " <<
dd.days() << " дней" << endl;
}
Программа из примера 5.7 должна вывести:
Двадцатый век содержал 36 524 дней
Двадцать первый век будет содержать 36 525 дней
Более 800 000 книг и аудиокниг! 📚
Получи 2 месяца Литрес Подписки в подарок и наслаждайся неограниченным чтением
ПОЛУЧИТЬ ПОДАРОКЧитайте также
18.1.3. Ограничения, связанные со временем
18.1.3. Ограничения, связанные со временем В 32-разрядных системах Linux, как и в большинстве систем Unix, переменная time_t является целым числом со знаком длиной 32 бита. Это означает, что в 10:14:07 вечера 18 января (четверг) 2038 года она переполнится. Поэтому время 10:14:08 вечера 18 января
if - Выполнение или не выполнение предложений в зависимости от условий
if - Выполнение или не выполнение предложений в зависимости от условий ifПозволяет выполнить или не выполняет определенные предложения в зависимости от заданного условияСинтаксис:if (condition) { statements}Аргументы:В целом, предложение if завершается закрывающей фигурной скобкой
§ 151. Со временем все портится
§ 151. Со временем все портится 10 октября 2008Автору совершенно очевидно, что со временем человечество работает все хуже и хуже (прогресс этому совершенно не мешает). Люди хотят затрачивать меньше сил и денег, получая все больше и больше взамен. То, что будет у людей через сто
20. Квадратный трехчлен, или Пакет Для Алгебраических Вычислений
20. Квадратный трехчлен, или Пакет Для Алгебраических Вычислений Основная трудность, с которой сталкивается программист в большинстве языков программирования, — необходимость при записи вычислений разбивать свои уравнения на мелкие части. Так, если требуется
Выполнение вычислений в запросах
Выполнение вычислений в запросах В строках запроса допускается выполнение вычислений. Для этого нужно просто заменить имя поля в предложении SELECT именем арифметического выражения. Допустим, вам нужно создать запрос для вычисления налога с продаж для складских запасов
12. Кодирование параллельных вычислений
12. Кодирование параллельных вычислений РезюмеЕсли ваше приложение использует несколько потоков или процессов, следует минимизировать количество совместно используемых объектов, где это только можно (см. рекомендацию 10), и аккуратно работать с
31. Не пишите код, который зависит от порядка вычислений аргументов функции
31. Не пишите код, который зависит от порядка вычислений аргументов функции РезюмеПорядок вычисления аргументов функции не определен, поэтому никогда не полагайтесь на то, что аргументы будут вычисляться в той или иной очередности.ОбсуждениеНа начальных этапах развития
3.14.5 Сопоставление с датой и временем
3.14.5 Сопоставление с датой и временем Пусть надо выделить дату и время, записанные в формате mm/dd/yy hh:mm:ss. Вот первая попытка: datetime = /(dd)/(dd)/(dd) (dd): (dd): (dd)/.Но такой образец распознает некоторые некорректные даты и отвергает правильные. Следующий вариант более избирателен.
7.2. Работа с конкретными датами (после точки отсчета)
7.2. Работа с конкретными датами (после точки отсчета) Большинству программ нужно работать только с датами, относящимися к будущему или недавнему прошлому. Для таких целей класса Time достаточно. Наиболее интересны методы mktime, local, gm и utc.Метод mktime создает новый объект Time на
7.14. Манипулирование временем без даты
7.14. Манипулирование временем без даты Иногда нужно работать с временем дня в виде строки. На помощь снова приходит метод strftime. Можно «разбить» время на часы, минуты и секундыt = Time.nowputs t.strftime("%H:%M:%S") # Печатается 22:07:45А можно только на часы и минуты (прибавив 30 секунд, мы даже
7.18. Работа с конкретными датами (до точки отсчета)
7.18. Работа с конкретными датами (до точки отсчета) В стандартной библиотеке Date есть одноименный класс для работы с датами, предшествующими полуночи 1 января 1970 года.Несмотря на некоторое перекрытие с классом Time, между ними есть существенные различия. Самое главное состоит
Функции работы со временем
Функции работы со временем Функция Краткое описание asctime преобразование времени из структуры (внутренней формы) в символьную строку ctime преобразование времени из длинного целого (long int) в строку символов gmtime преобразование времени из целого (int) в
Пример A-8. days-between: Подсчет числа дней между двумя датами
Пример A-8. days-between: Подсчет числа дней между двумя датами #!/bin/bash# days-between.sh: Подсчет числа дней между двумя датами.# Порядок использования: ./days-between.sh [M]M/[D]D/YYYY [M]M/[D]D/YYYYARGS=2 # Ожидается два аргумента из командной строки.E_PARAM_ERR=65 # Ошибка в числе ожидаемых
Объектно-ориентированный стиль вычислений
Объектно-ориентированный стиль вычислений Обратимся теперь к фундаментальным свойствам класса POINT и попытаемся понять, как устроено типичное тело подпрограммы и составляющие его инструкции. Далее выясним, каким образом класс и его компоненты могут использоваться
Повторение вычислений
Повторение вычислений Инструкция повторного выполнения рассматривалась при обсуждении исключительных ситуаций (лекция 12). Она появляется только в предложении rescue, повторно запуская тело подпрограммы, работа которой была