-2

I have a list of dates/times items in PHP array that are formatted like this:

2019-03-19 00:00:00
2019-03-19 02:30:00
2019-03-19 05:00:00
2019-03-19 14:30:00
2019-03-19 23:59:59

etc.

I'm sure this is easy, I just can't wrap my head around it. What equation do I use to display the item that is closest to the current time without going over.

So if current time is 22:00:00, I would want to display item 14:30:00, rather than 23:59:59.

Nick
  • 138,499
  • 22
  • 57
  • 95
Bryan
  • 69
  • 8

3 Answers3

2

Since your times are in Y-m-d H:i:s you can just compare them as strings and use a simple foreach loop to get your result:

$dates = array('2019-03-19 00:00:00',
               '2019-03-19 02:30:00',
               '2019-03-19 05:00:00',
               '2019-03-19 14:30:00',
               '2019-03-19 23:59:59');
$now = date('Y-m-d H:i:s');
$latest = '';
// add sort($dates) here if they are not already sorted.
foreach ($dates as $date) {
    if ($date > $now) break;
    $latest = $date;
}
echo $latest;

Demo on 3v4l.org

Note this code assumes your dates are already sorted, if not, add sort($dates) before the foreach loop.

Nick
  • 138,499
  • 22
  • 57
  • 95
  • This will work only if the date are sorted - this is not part of the OP question (it maybe but he didn't mention it) - so better to add that to the answer – dWinder Mar 20 '19 at 08:22
0

First of all convert all the Dates to this format

$changed_date_1 = date('YmdHis', strtotime($orignaldate_1));
$changed_date_2 = date('YmdHis', strtotime($orignaldate_2));
$changed_date_3 = date('YmdHis', strtotime($orignaldate)_3);

so 2019-03-19 00:00:00 will become 20190319000000, and so on, now they can be compared easily. than run a foreach loop in which iterate through all these date

$closestdate= date('Y-m-d H:i:s');//intaily set it to current date
$closest_difference= 99999999999999999;//intaily set a big value, more than 15 digits
foreach($datesArray as $item){
   $difference = $item - date('YmdHis');
   if($difference < $closest_difference){
      $closes_difference = $difference;
      $closestdate = $item;//this item is closest one. in next iteration this may change
   }
}
echo $Closesdate;
Sanaullah Ahmad
  • 474
  • 4
  • 12
0
/**
 * Gets the nearest moment of the same day as $today.
 *
 * @param string[] $dates - A list of dates (needed format: "Y-m-d H:i:s")
 * @param string|null $today - The date used for comparaison. (default is current date)
 * @return string|bool - Returns the nearest date, or false.
 */
function getNearestDate(array $dates, ?string $today = null) {
    if (!$today) {
        $today = date('Y-m-d H:i:s');
    }

    $fnDT = function($d) {
        return DateTime::createFromFormat('Y-m-d H:i:s', $d);
    };

    usort($dates, function($a, $b) use ($fnDT, $today) {
        $da = abs($fnDT($today)->getTimestamp() - $fnDT($a)->getTimestamp());
        $db = abs($fnDT($today)->getTimestamp() - $fnDT($b)->getTimestamp());

        return $da - $db;
    });

    $nearest = $dates[0];

    if ($fnDT($nearest)->format('Y-m-d') !== $fnDT($today)->format('Y-m-d')) {
        print_r('No date of the same day.');
        return false;
    }

    return $nearest;
}

Test it on 3v4l.org

Kévin Bibollet
  • 3,573
  • 1
  • 15
  • 33