<?php
class DateTimeExtended extends DateTime {
public function __get($name) {
switch ($name) {
case 'year':
return (int)$this->format('Y');
case 'month':
return (int)$this->format('n');
case 'day':
return (int)$this->format('j');
case 'hour':
return (int)$this->format('G');
case 'minute':
return (int)$this->format('i');
case 'second':
return (int)$this->format('s');
case 'dayOfWeek':
return (int)$this->format('w');
case 'dayOfYear':
return (int)$this->format('z');
case 'weekOfYear':
return (int)$this->format('W');
case 'daysInMonth':
return (int)$this->format('t');
case 'timestamp':
return (int)$this->format('U');
default:
throw new InvalidArgumentException(sprintf('Unknown property "%s".', $name));
}
}
public static function createFromFormat($format, $time, $tz = null) {
if ($tz) {
$date = parent::createFromFormat($format, $time, $tz);
} else {
$date = parent::createFromFormat($format, $time);
}
$errors = static::getLastErrors();
if ($errors['warning_count'] !== 0 || $errors['error_count'] !== 0) {
throw new InvalidArgumentException(sprintf('Unable to parse date "%s" by pattern "%s".', $time, $format));
}
if (!$date instanceof self) {
return new static($date->format('Y-m-d H:i:s'), $date->getTimeZone());
}
return $date;
}
public function format($format) {
$format = preg_replace_callback('/(?:f|[Мм]есяца?|[Дд]еньнед(?:ели)?)/u', array($this, 'replaceFormatCallback'), $format);
return parent::format($format);
}
public function replaceFormatCallback(array $matches) {
switch ($matches[0]) {
case 'f':
return mb_strtolower(en_get_month_name($this->month));
case 'Месяц':
return ru_get_month_name($this->month);
case 'Месяца':
return ru_get_month_name($this->month, 2);
case 'месяц':
return mb_strtolower(ru_get_month_name($this->month));
case 'месяца':
return mb_strtolower(ru_get_month_name($this->month, 2));
case 'Деньнедели':
return ru_get_weekday_name($this->dayOfWeek);
case 'Деньнед':
return ru_get_weekday_name($this->dayOfWeek, true);
case 'деньнедели':
return mb_strtolower(ru_get_weekday_name($this->dayOfWeek));
case 'деньнед':
return mb_strtolower(ru_get_weekday_name($this->dayOfWeek, true));
}
return $matches[0];
}
public static function convert($from, $to, $value) {
return static::createFromFormat($from, $value)->format($to);
}
public static function check($format, $value) {
try {
static::createFromFormat($format, $value);
} catch (InvalidArgumentException $e) {
return false;
}
return true;
}
}
$t = microtime(true);
for ($i = 0; $i < 2000; $i++) {
DateTimeExtended::convert('Y-m-d', 'd.m.Y H:i:s', '2000-01-01');
}
echo 'DateTimeExtended:'.(microtime(true) - $t)."\n";
//----------------------------------------------------------------------------------------------------
function int_pad($number, $count = 2) {
return str_pad((int)$number, $count, '0', STR_PAD_LEFT);
}
function Date_parseDate($format, $str) {
$patterns['Y'] = array('(\d{4})', 'year');
$patterns['y'] = array('(\d{2})');
$patterns['m'] = array('(\d{2})', 'month');
$patterns['n'] = array('(\d{1,2})', 'month');
$patterns['d'] = array('(\d{2})', 'day');
$patterns['j'] = array('(\d{1,2})', 'day');
$patterns['H'] = array('(\d{2})', 'hour');
$patterns['h'] = array('(\d{1,2})', 'hour');
$patterns['i'] = array('(\d{1,2})', 'minute');
$patterns['M'] = array('(\d{2})', 'minute');
$patterns['s'] = array('(\d{1,2})', 'second');
$patterns['U'] = array('(-?\d+)');
$parameters = array();
$out_types = array();
for ($i = 0; $i < mb_strlen($format); $i++) {
$char = mb_substr($format, $i, 1);
if (isset($patterns[$char])) {
$out_types[] = $char;
$parameters[] = $patterns[$char][0];
} else {
$parameters[] = $char;
}
}
if (!preg_match('/^'.implode($parameters).'$/u', $str, $out)) {
throw new RuntimeException(sprintf('Не удалось распарсить дату "%s" по шаблону "%s".', $str, $format));
}
// FIX
/* $date['year'] = (int)date('Y');
$date['month'] = (int)date('n');
$date['day'] = (int)date('j');
$date['hour'] = (int)date('h');
$date['minute'] = (int)date('i');
$date['second'] = (int)date('s');*/
$date['year'] = 1970;
$date['month'] = 1;
$date['day'] = 1;
$date['hour'] = 0;
$date['minute'] = 0;
$date['second'] = 0;
for ($i = 0; $i < count($out_types); $i++) {
$pattern = $patterns[$out_types[$i]];
if (isset($pattern[1])) {
$date[$pattern[1]] = (int)$out[$i + 1];
} else {
if ($out_types[$i] === 'U') {
$standard_date = getdate($out[$i + 1]);
$date['year'] = $standard_date['year'];
$date['month'] = $standard_date['mon'];
$date['day'] = $standard_date['mday'];
$date['hour'] = $standard_date['hours'];
$date['minute'] = $standard_date['minutes'];
$date['second'] = $standard_date['seconds'];
}
if ($out_types[$i] === 'y') {
$date['year'] = $out[$i + 1] + ($out[$i + 1] < 30 ? 2000 : 1900);
}
}
}
return $date;
}
function Date_createDate($format, $date) {
$patterns['Y'] = int_pad($date['year'], 4);
$patterns['y'] = int_pad($date['year'] - (int)($date['year'] / 100) * 100);
$patterns['m'] = int_pad($date['month']);
$patterns['n'] = $date['month'];
$patterns['d'] = int_pad($date['day']);
$patterns['j'] = $date['day'];
$patterns['H'] = int_pad($date['hour']);
$patterns['h'] = $date['hour'];
$patterns['G'] = int_pad($date['hour']);
$patterns['g'] = $date['hour'];
$patterns['i'] = int_pad($date['minute']);
$patterns['M'] = int_pad($date['minute']);
$patterns['s'] = int_pad($date['second']);
$patterns['U'] = mktime($date['hour'], $date['minute'], $date['second'], $date['month'], $date['day'], $date['year']);
$parameters = array();
for ($i = 0; $i < mb_strlen($format); $i++) {
$char = mb_substr($format, $i, 1);
$parameters[] = isset($patterns[$char]) ? $patterns[$char] : $char;
}
$text = implode($parameters);
$replace['/Месяца/eu'] = 'ru_get_month_name('.(int)$date['month'].', 2)';
$replace['/Месяц/eu'] = 'ru_get_month_name('.(int)$date['month'].')';
$replace['/месяца/eu'] = 'mb_strtolower(ru_get_month_name('.(int)$date['month'].', 2))';
$replace['/месяц/eu'] = 'mb_strtolower(ru_get_month_name('.(int)$date['month'].'))';
$replace['/F/eu'] = 'en_get_month_name('.(int)$date['month'].')';
$replace['/f/eu'] = 'mb_strtolower(en_get_month_name('.(int)$date['month'].'))';
if ($patterns['U']) {
$replace['/Деньнедели/eu'] = 'ru_get_weekday_name(date("w", '.(int)$patterns['U'].'))';
$replace['/Деньнед/eu'] = 'ru_get_weekday_name(date("w", '.(int)$patterns['U'].'), true)';
$replace['/деньнедели/eu'] = 'mb_strtolower(ru_get_weekday_name(date("w", '.(int)$patterns['U'].')))';
$replace['/деньнед/eu'] = 'mb_strtolower(ru_get_weekday_name(date("w", '.(int)$patterns['U'].'), true))';
}
return preg_replace(array_keys($replace), $replace, $text);
}
function Date_checkDate($format, $str) {
$patterns['Y'] = array('(\d{4})', 'year');
$patterns['y'] = array('(\d{2})');
$patterns['m'] = array('(\d{2})', 'month');
$patterns['n'] = array('(\d{1,2})', 'month');
$patterns['d'] = array('(\d{2})', 'day');
$patterns['j'] = array('(\d{1,2})', 'day');
$patterns['H'] = array('(\d{2})', 'hour');
$patterns['h'] = array('(\d{1,2})', 'hour');
$patterns['i'] = array('(\d{1,2})', 'minute');
$patterns['M'] = array('(\d{2})', 'minute');
$patterns['s'] = array('(\d{1,2})', 'second');
$patterns['U'] = array('(-?\d+)');
$parameters = array();
$out_types = array();
for ($i = 0; $i < mb_strlen($format); $i++) {
$char = mb_substr($format, $i, 1);
if (isset($patterns[$char])) {
$out_types[] = $char;
$parameters[] = $patterns[$char][0];
} else {
$parameters[] = $char;
}
}
return (bool)preg_match('/^'.implode($parameters).'$/u', $str, $out);
}
function Date_convert($format_from, $format_to, $str) {
$date = Date_parseDate($format_from, $str);
return Date_createDate($format_to, $date);
}
$t = microtime(true);
for ($i = 0; $i < 2000; $i++) {
Date_convert('Y-m-d', 'd.m.Y H:i:s', '2000-01-01');
}
echo 'DateConvert: '.(microtime(true) - $t)."\n";
preferences:
36.18 ms | 402 KiB | 5 Q