通过PHP循环遍历日期
我试图通过PHP来循环日期。目前我的代码被卡在循环110307中。我需要日期格式在yymmdd中。以下是我尝试使用:通过PHP循环遍历日期
<?php
$check_date = '100227';
$end_date = '100324';
while($check_date != $end_date){
$check_date = date("ymd", strtotime("+1 day", strtotime($check_date)));
echo $check_date . '<br>';
}
?>
strtotime
解释 “100227” 作为时间10时02分27秒的今天,不是2010-02-27。所以在第一步之后,$check_date
(今天)是“110307”。在随后的所有步骤中,“110307”再次被解释为今天的时间,将$check_date
再次解释为“110307”。
用于重复日期的绝招是利用mktime的正常化日期的能力,这样的事情:
$date_arr = array(27,2,2010);
$end_date = "100324";
do {
$check_date = gmdate('ymd', gmmktime(0,0,0,$date_arr[1],$date_arr[0]++,$date_arr[2]));
echo $check_date."\n";
} while($end_date!=$check_date);
下面是我用的是代码的一部分,或许可以得到改善,取决于你使用的PHP版本。
//usage
$Iterator=class Dates_DateIterator::factory('Daily',
new Datetime('20100227'),
new Datetime('20100324'));
foreach($Iterator as $i=>$day){
var_dump($i);
var_dump($day);
}
//code lib
abstract class Dates_DateIterator implements Iterator
{
/**
* Factory method, saves some code, also enable me to put everything in the same class
* as we use Autoload to load classes.
*/
static public function factory($cycle,DateTime $DateI,DateTime $DateII){
switch($cycle){
case 'Daily':
return new DaysIterator($DateI,$DateII);
case 'Weekly':
return new WeeksIterator($DateI,$DateII);
case 'Monthly':
return new MonthsIterator($DateI,$DateII);
case 'Yearly':
return new YearsIterator($DateI,$DateII);
default:
throw(new Exception('No valid cycle was chosen to iterate over'));
}
}
/**
* @var DateTime represents the start range.
*/
public $FromDate;
/**
* @var DateTime represents the end range.
*/
public $ToDate;
/**
* @var DateTime Current Date.
*/
protected $CurrentDate;
public function __construct(DateTime $DateI,DateTime $DateII)
{
if($DateII->format('U') > $DateI->format('U'))
{
$this->FromDate=$DateI;
$this->ToDate=$DateII;
$this->CurrentDate=$DateI;
}
else
{
$this->FromDate=$DateII;
$this->ToDate=$DateI;
$this->CurrentDate=$DateII;
}
}//EOF constructor
/**
* @return DateTime
*/
public function getClonedCurrent(){
return clone($this->CurrentDate);
}
public function current()
{
return $this->CurrentDate;
}//EOF current
public function currentDate()
{
return $this->CurrentDate->format('Ymd');
}//EOF current
public function rewind()
{
$this->CurrentDate=$this->FromDate;
}//EOF rewind
public function valid()
{
//Kill hours/minutes/seconds. If we are to add hours and minutes iterators, we will need to rethink this.
return (floor($this->CurrentDate->format('U')/(3600*24)) <= floor($this->ToDate->format('U')/(3600*24)));
}//EOF valid
}//EOF CLASS DateIterator
class DaysIterator extends SiTEL_Dates_DateIterator
{
public function __construct(DateTime $DateI,DateTime $DateII)
{
parent::__construct($DateI,$DateII);
}//EOF constructor
public function next()
{
$this->CurrentDate->modify('+1 day');
}//EOF next
public function key()
{
return $this->CurrentDate->format('d');
}//EOF key
}//EOD CLASS DaysIterator
哇,这是超重量级。 – 2011-03-06 06:30:32
@Paul Schreiber阅读整个事情,它是一个更大的框架/ lib的一部分。重要的是,你是对的,因为我需要针对不同的周期准确地使用相同的代码(它是事件中继器计算器的一部分)。但是......把它放在这里花的时间比写下它的时间少:-) – 2011-03-06 06:33:13
我可以看到。似乎有一个很大的性能影响,可以导入一个框架并分配/实例化/销毁n个对象。 – 2011-03-06 06:34:54
尝试使用unix时间戳并每次添加86400。这要比致电strtotime()
快。你可以lookup timestamp conversions online。
<?php
$check_date = 1267228800; // '2010-02-27';
$end_date = 1269388800; // '2010-03-24';
while($check_date != $end_date){
$check_date += 86400;
echo date("Ymd", $check_date) . '<br>';
}
?>
以下是我喜欢做它:
$startDate = new DateTime('20100227');
$endDate = new DateTime('20100324');
while ($startDate <= $endDate) {
// your code here
...
// go to the next day
$startDate->add(new DateInterval('P1D'));
}
我觉得这个人更清洁,它不需要像84600那样硬编码值。
什么是PHP版本? – 2011-03-06 06:20:14
@Itay Moav:版本5.2.17。 – shinjuo 2011-03-06 06:23:11
然后而不是'modify('+ 1 day');'例如,你可以使用' - > add'方法。 – 2011-03-06 06:36:56