Should I store the result of an function into an array? - php

I have a function like this:
function time_elapsed_string($ptime)
{
$date_time = strtotime("1348-10-10 04:30:01") + $ptime;
$year = date("Y",$date_time);
$month = date("m",$date_time);
$day = date("d",$date_time);
$time = date("H:i:s",$date_time);
$etime = time() - $ptime + 1;
$a = array( 31536000 => 'year',
2592000 => 'month',
86400 => 'day',
3600 => 'hour',
60 => 'minute',
1 => 'second'
);
foreach ($a as $secs => $str)
{
$d = $etime / $secs;
if ($d >= 1)
{
$r = round($d);
// EX:
return array('date' => $day.'-'.$month.'-'.$year, // 2016-02-20
'time' => $time, // 03:30:04
'difference' => $r . ' ' . $str . ' ago' // 2 month ago
);
}
}
}
And I use it like this:
$ptime = 1470692661;
$html = '<span title="date: '.time_elapsed_string($ptime)['date'].' time: '.time_elapsed_string($ptime)['time'].'">in '.time_elapsed_string($ptime)['difference'].'<span>';
As you see, I'm using of that function's result like this:
time_elapsed_string($ptime)['date']
ime_elapsed_string($ptime)['time']
time_elapsed_string($ptime)['difference']
In fact I'm calling that function every time I need one of its results. Is that right? Or should I call it once and store it into an array?
Note: My code works as well.

Counting time elapsed since some date/time like this is mauvais ton.
DateTime has been available since PHP 5.2.0 and tonns of people underestimate it. Why don't you use this instead of loops and ifs?
$create_time = "2016-08-02 12:35:04";
$current_time="2016-08-02 16:16:02";
$dtCurrent = DateTime::createFromFormat('Y-m-d H:i:s', $current_time);
// to use current timestamp, use the following:
//$dtCurrent = new DateTime();
$dtCreate = DateTime::createFromFormat('Y-m-d H:i:s', $create_time);
$diff = $dtCurrent->diff($dtCreate);
Now, you can format the result however you want:
$interval = $diff->format("%h hours %i minutes %s seconds");
This will give a clean 3 hours 40 minutes 58 seconds without any arrays, which is better.
UPDATE
There is a general solution to get hours / minutes / seconds via regex:
$interval = $diff->format("%y years %m months %d days %h hours %i minutes %s seconds");
// now remove zero values
$interval = preg_replace('/(^0| 0) (years|months|days|hours|minutes|seconds)/', '', $interval);
UPDATE 2
As of your comment:
Look, I want to use your approach .. but I really cannot implement it .. Actually I need three things: time, date, difference ..! But your approach doesn't give me them..
Well, we already know how to get the difference, it's the $interval variable described above.
To get time and date, you can get it from the $dtCreate variable by, again, using format:
$time = $dtCreate->format('H:i:s');
$date = $dtCreate->format('d-m-Y');

This is a no brainer.
Yes - store the function call result of time_elapsed_string($ptime) in an array, then use that to access your results. You're wasting CPU cycles otherwise!
// call it once
$result = time_elapsed_string($ptime);
// then use:
$result['date'];
$result['time'];
$result['difference'];

Related

PHP - subtracting time return nothing

I found a function form SC to output human readable time. like `
5 hours, 1 hour, 5 years, etc
function human_time ($time)
{
$time = time() - strtotime($time); // to get the time since that moment
$tokens = array (
31536000 => 'year',
2592000 => 'month',
604800 => 'week',
86400 => 'day',
3600 => 'hour',
60 => 'minute',
1 => 'second'
);
foreach ($tokens as $unit => $text) {
if ($time < $unit) continue;
$numberOfUnits = floor($time / $unit);
return $numberOfUnits.' '.$text.(($numberOfUnits>1)?'s':'');
}
}
And I have time as string: 2013-09-28 20:55:42
when I call this function human_time('2013-09-28 20:55:42')
then it return nothing, why ?
I have added strtotime in above function.
Please tell me what is wrong.
This is no ready-to-use code, but rather supposed to guide you the right way:
$then = new DateTime($time); // you might need to format $time using strtotime or other functions depending on the format provided
$now = new DateTime();
$diff = $then->diff($now, true);
echo $diff->format('Your style goes here');
See DateTime Manual for further documentation or feel free to ask here.
Edit: Link fixed.
Use example :
echo time_elapsed_string('2013-05-01 00:22:35');
echo time_elapsed_string('2013-05-01 00:22:35', true);
Output :
4 months ago
4 months, 2 weeks, 3 days, 1 hour, 49 minutes, 15 seconds ago
Link to the function.

Script to translate a mySQL datetime column to 'starts in x days/hours'

I have a MySQL table with events in it. Each event has a datetime column that indicates when it starts.
I'm looking for a way to produce a string similar to this using PHP:
'event X starts in 2 hours'
Should also work for days, weeks and months:
'event X starts in 5 days/weeks/months'
You should have some variable with the number of seconds till your date available. My example function is below.
<?php
function timeRemaining($total) {
if (!$total || $total <= 0) return false;
// define your ranges here (desc order), the keys will go to output.
$elements = array(
"years" => 60*60*24*30*12,
"months" => 60*60*24*30,
"weeks" => 60*60*24*7,
"days" => 60*60*24,
"hours" => 60*60,
"minutes" => 60,
"seconds" => 1
);
// compute in a cycle to compress the code
$return = array();
foreach ($elements as $name => $dur) {
$return[$name] = floor($total / $dur);
$total -= $return[$name] * $dur;
}
// return data in the array form
return $return;
}
// how much till new year?
echo "<pre>",
print_r(timeRemaining(mktime(0,0,0,1,1,2012)-time()));
echo "</pre>";
?>
Just copy-paste into any php file for testing, as an example it returns the array with years, months etc remaining till new year. You can tailor the output for your needs by feeding the return value to another string-generating function, just don't forget to check the value against false, which'll mean the time has passed.
Please note that the months use a simplified 30-days range, and the year here is set to 360 days, not 365.25 as in the real world.
Hope it will be of use.
To use this I first changed the format of the date to:
Select DATE_FORMAT(date_of, '%d/%m/%Y') as example from tbl
The php Function:
<?php
function days_ago($time)
{
$today = mktime(0, 0, 0, date('m'), date('d'), date('Y'));
$time_array = explode("/", $time);
if(count($time_array) < 2)
{
$time = "N/A";
}
else
{
$time = mktime(0, 0, 0, date($time_array[1]), date($time_array[0]), date($time_array[2]));
$daysAgo = $today - $time;
$time = ($daysAgo/86400);
}
return $time;
}
?>
I took the following snippet from the here.
<?php
$dateDiff = $date1 - $date2;
$fullDays = floor($dateDiff/(60*60*24));
$fullHours = floor(($dateDiff-($fullDays*60*60*24))/(60*60));
$fullMinutes = floor(($dateDiff-($fullDays*60*60*24)-($fullHours*60*60))/60);
echo "Differernce is $fullDays days, $fullHours hours and $fullMinutes minutes.";
?>
$date1 would be the database date, $date2 would be the current date. Does that help?

Calculates difference between two dates in PHP [duplicate]

This question already has answers here:
Get interval seconds between two datetime in PHP?
(8 answers)
Closed last year.
HI, i have a couple of posts in my MySql database server, one of the info content in each post is the date and time in the format datetime (Ex. 2010-11-26 21:55:09) when the post was made.
So, i want to retrive the actual date and time from the SQL server with the function NOW() and calculates how many seconds or minutes or hours or days ago was post the info.
I dont know how to create this php script but i know that for sure is allready made, so thanks for any help.
you could use the date_diff() function
http://php.net/manual/en/function.date-diff.php
Something like...
<?php
$now = time();
$then = $posttime;
$diff = date_diff($now,$then);
echo $diff->format('%R%d days'); #change format for different timescales
?>
edit --
I actually solve this issue on one of my twitter apps using this function...
function time_since ( $start )
{
$end = time();
$diff = $end - $start;
$days = floor ( $diff/86400 ); //calculate the days
$diff = $diff - ($days*86400); // subtract the days
$hours = floor ( $diff/3600 ); // calculate the hours
$diff = $diff - ($hours*3600); // subtract the hours
$mins = floor ( $diff/60 ); // calculate the minutes
$diff = $diff - ($mins*60); // subtract the mins
$secs = $diff; // what's left is the seconds;
if ($secs!=0)
{
$secs .= " seconds";
if ($secs=="1 seconds") $secs = "1 second";
}
else $secs = '';
if ($mins!=0)
{
$mins .= " mins ";
if ($mins=="1 mins ") $mins = "1 min ";
$secs = '';
}
else $mins = '';
if ($hours!=0)
{
$hours .= " hours ";
if ($hours=="1 hours ") $hours = "1 hour ";
$secs = '';
}
else $hours = '';
if ($days!=0)
{
$days .= " days ";
if ($days=="1 days ") $days = "1 day ";
$mins = '';
$secs = '';
if ($days == "-1 days ") {
$days = $hours = $mins = '';
$secs = "less than 10 seconds";
}
}
else $days = '';
return "$days $hours $mins $secs ago";
}
You pass it in a unix timestamp of the time to check (the post time) and it returns the various string.
As billythekid said, you can use the date_diff() function if you are using PHP5.3+, if you are not then there are various methods. As shown by other posters. The quickest method in MySQL if you want to know the time split in to the "hours:mins:secs" hierarchy is to use the TIMEDIFF() function.
SELECT TIMEDIFF(NOW(), '2010-11-26 12:00:00');
If you want it as seconds, use the unix timestamp features in MySQL or in PHP, you can convert MySQL dates to PHP quickly using strtotime().
Usually, you do this kind of thing in a query, but MySQL isn't very good with intervals (it would be very easy with PostgreSQL). You could convert it to unix timestamp, then it would give the number of seconds between the two dates :
SELECT UNIX_TIMESTAMP() - UNIX_TIMESTAMP(your_datetime_column);
I thought about DATEDIFF, but it only returns the number of days between the two dates.
You can do it in PHP, for instance, with DateTime class :
$date1 = new DateTime();
$date2 = new Datetime('2010-11-26 12:00:00');
var_dump($date1->diff($date2));
(There's a procedural way to do this, if you're not a fan of OOP.)
This is definitely the solution I'd use if I can't do it with the RDBMS. DateTime::diff returns a DateInterval object, which contains the number of seconds, minutes, hours, days, etc. between the two dates.
You could also do it with timestamps in PHP :
$num_sec = time() - strtotime('2010-11-26 12:00:00');
Which would return the same thing as the SQL query.
An easy solution is possible from within the SQL Query:
SELECT UNIX_TIMESTAMP(NOW()) - UNIX_TIMESTAMP(post_date) AS seconds_ago FROM posts
Documentation here: MySQL Ref
I actually needed to do this in PHP myself and while billythekid's post was in the right direction it fell short. I've minimized the code though it should be clear that the second parameter is from a database with a DATETIME column type.
<?php
$interval = date_diff(date_create(date('Y-m-d H:i:s')), date_create($row1['date']));
echo $interval->format('%R%a days');
//Database: 2019-02-22
//PHP's date: 2018-07-07
//Result: +306 days
?>
A reminder of the obvious: you can also just use substr($interval->format('%R%a days'),1) if you need just the integer.

Convert dates to hours

I'm trying to work with dates for the first time, I did it something about that with Flash but it's different.
I have two different dates and I'd like to see the difference in hours and days with them, I've found too many examples but not what I'm loking for:
<?php
$now_date = strtotime (date ('Y-m-d H:i:s')); // the current date
$key_date = strtotime (date ("2009-11-21 14:08:42"));
print date ($now_date - $key_date);
// it returns an integer like 5813, 5814, 5815, etc... (I presume they are seconds)
?>
How can I convert it to hours or to days?
The DateTime diff function returns a DateInterval object. This object consists of variabeles related to the difference. You can query the days, hours, minutes, seconds just like in the example above.
Example:
<?php
$dateObject = new DateTime(); // No arguments means 'now'
$otherDateObject = new DateTime('2008-08-14 03:14:15');
$diffObject = $dateObject->diff($otherDateObject));
echo "Days of difference: ". $diffObject->days;
?>
See the manual about DateTime.
Sadly, it's a PHP 5.3> only feature.
Well, you can always use date_diff, but that is only for PHP 5.3.0+
The alternative would be math.
How can I convert it [seconds] to hours or to days?
There are 60 seconds per minute, which means there are 3600 seconds per hour.
$hours = $seconds/3600;
And, of course, if you need days ...
$days = $hours/24;
If you dont have PHP5.3 you could use this method from userland (taken from WebDeveloper.com)
function date_time_diff($start, $end, $date_only = true) // $start and $end as timestamps
{
if ($start < $end) {
list($end, $start) = array($start, $end);
}
$result = array('years' => 0, 'months' => 0, 'days' => 0);
if (!$date_only) {
$result = array_merge($result, array('hours' => 0, 'minutes' => 0, 'seconds' => 0));
}
foreach ($result as $period => $value) {
while (($start = strtotime('-1 ' . $period, $start)) >= $end) {
$result[$period]++;
}
$start = strtotime('+1 ' . $period, $start);
}
return $result;
}
$date_1 = strtotime('2005-07-31');
$date_2 = time();
$diff = date_time_diff($date_1, $date_2);
foreach ($diff as $key => $val) {
echo $val . ' ' . $key . ' ';
}
// Displays:
// 3 years 4 months 11 days
TheGrandWazoo mentioned a method for php 5.3>. For lower versions you can devide the number of seconds between the two dates with the number of seconds in a day to find the number of days.
For days, you do:
$days = floor(($now_date - $key_date) / (60 * 60 * 24))
If you want to know how many hours are still left, you can use the modulo operator (%)
$hours = floor((($now_date - $key_date) % * (60 * 60 * 24)) / 60 * 60)
<?php
$now_date = strtotime (date ('Y-m-d H:i:s')); // the current date
$key_date = strtotime (date ("2009-11-21 14:08:42"));
$diff = $now_date - $key_date;
$days = floor($diff/(60*60*24));
$hours = floor(($diff-($days*60*60*24))/(60*60));
print $days." ".$hours." difference";
?>
I prefer to use epoch/unix time deltas. Time represented in seconds and as such you can very quickly divide by 3600 for hours and divide by 24*3600=86400 for days.

Unix timestamp to days, hours, minutes

So, I have a field in my users table named last_active which updates every time a user reloads a page. It's stored in unix timestamp.
I would like to output it like this: Last online: 4 d 18 h 19 m ago
How would one do that? Can you do it with php's date()?
Thank you.
You could achieve this directly in MySQL if you like:
select date_format(from_unixtime(current_timestamp - last_timestamp),
'Last online: %e days, %k hours, %i minutes, %s seconds ago.');
(current_timestamp can be replaced with unix_timestamp(now()) if you want it calculated in-place)
DATE_FORMAT allows you to have a custom string based on a specific date. If you populate its date with the difference between two timestamps, it will work as you've asked.
The above solution will only work if it's under a month; if you want days of the year, use %j. The documentation for the function shows more.
The simplest approach to this is to take the last_active timestamp, and the current timestamp with time(). Then subtract the last active from the current timestamp, and then you simply divide the result with the amount of seconds in a day to get difference in days, amount of seconds in an hour to get difference in hours and so on.
This approach may be slightly inaccurate in some special cases (leap years, etc.) but it should suffice for your simpler usecase
After finding dozens of broken or half-there solutions, I built the following function for UNIX timestamps.
You can limit the detail level ...
echo timeDiff(1350297908); will show "5 minutes, 42 seconds ago".
echo timeDiff(1350297908, 1); will just show "5 minutes ago".
function timeDiff( $from, $levels=7 ){
$now = time();
$diff = ($from > $now) ? $from - $now : $now - $from;
$status = ($from > $now) ? ' away' : ' ago';
$times = array(31536000, 2628000, 604800, 86400, 3600, 60, 1);
$words = array('year', 'month', 'week', 'day', 'hour', 'minute', 'second');
$str = array();
foreach ($times as $k=>$v){
$val = floor($diff/$v);
if ($val) {
$str[] = $val .' '. $words[$k] . ($val==1 ? '' : 's');
$levels--;
}
$diff %= $v;
if ($levels==0) break;
}
return implode(', ', $str) . $status;
}
I wrote this simple function when I need this kind of solution (it gets minutes as input):
function minutes_to_time($minutes)
{
$obj = "";
// extract days
$days = floor($minutes/(1440)); # Divide on the daily minutes 60 min * 24 hours
# echo "Days: " . $days;
// extract hours
$hours = floor(($minutes-($days*1440))/60);
# echo " Hours: " . $hours;
// extract left minutes
$minutes = ($minutes-($days*24*60)-($hours*60));
# echo " Minutes: " . $minutes;
if ($days > 0)
{
$obj .= $days . "d ";
}
if ($hours > 0)
{
$obj .= $hours . "h ";
}
if ($minutes >= 0)
{
$obj .= $minutes . "m ";
}
$obj .= "ago";
return $obj;
}

Categories