I'm trying to find the current date and time, convert to a unix timestamp, and then subtract a previous time. I've tried multiple approaches and have received errors or incorrect values. So far here is my code:
// Current date and time
$currentTime = date("Y-m-d H:i:s");
// Convert datetime to Unix timestamp
$currentTimestamp = strtotime($currentTime);
// Create previous date and time
$previousTime = new DateTime("2021-04-17 13:00:00");
// Specify display format
$previousTime->format('Y-m-d H:i:s');
// Convert to Unix timestamp
$previousTimestamp = strtotime($previousTime);
// Subtract previous time from current time
$time = $currentTimestamp - $previousTimestamp;
// Display result
echo $time;
So how it should work is if the current date and time is for example: 2021-04-17 14:00:00 and the previous date and time is 2021-04-17 13:00:00, then the result should be 3600. Or if there is a two hour gap, then it's 7200, etc. With this current code, the error I'm getting is:
Uncaught TypeError: strtotime(): Argument #1 ($datetime) must be of
type string, DateTime
And other code I have tried doesn't return the correct time difference or other errors are thrown. How do I get the correct time difference?
You need to read the docs about what each function expects as an argument and what each returns. You're mixing a timestamp (an integer) with a DateTime object. If you want to do date calculations, you'll need to use the same format for both. Since you're looking for the number of seconds difference, it's probably simpler to use timestamp integers.
This code gives you an integer timestamp:
$currentTime = date("Y-m-d H:i:s");
$currentTimestamp = strtotime($currentTime);
But note that "now" is the default return value for the time() function, so you can just do this instead:
$currentTimestamp = time();
And you don't need this:
// This gives you a DateTime object
$previousTime = new DateTime("2021-04-17 13:00:00");
// This doesn't change the internal representation,
// it just returns a value that you're not using.
$previousTime->format('Y-m-d H:i:s');
// This function expects a string, but you're giving an object.
$previousTimestamp = strtotime($previousTime);
Instead, you can just pass your formatted date string directly to strtotime() and it will return an integer timestamp:
$previousTimestamp = strtotime("2021-04-17 13:00:00");
Now you have two integers representing seconds, so you can just subtract them to get the number of seconds between. Your prog becomes:
$currentTimestamp = time();
$previousTimestamp = strtotime("2021-04-17 13:00:00");
$diff = $currentTimestamp - $previousTimestamp;
echo $diff;
Or just:
echo time() - strtotime("2021-04-17 13:00:00");
Related
In my table, I have a variable $duration which is stored in minutes.
And I also have a time variable. Let it be $time1.
$time1=date('H:i:s',$time);
$duration=1000; //minutes
$time2= secondsToTime($duration*60);
I convert the $duration to time format using the function given below.
function secondsToTime($seconds) {
$dtF = new DateTime("#0");
$dtT = new DateTime("#$seconds");
return $dtF->diff($dtT)->format('%h:%i:%s');
}
So in $time2, i have something like this stored 11:12:13
And in $time1 i have something like this stored 01:10:19
I want to perform $total=$time1+$time2;
So, I converted $time2 into time format.
$timeform= new DateTime($time2);
$newtime2= $timeform->format('H:i:s');
Now, I add $total=$time1+$newtime2;
But echo date('H:i:s',$total);gave me following error:
Notice: Object of class DateTime could not be converted to int
The second argument of date() should be a timestamp (i.e. an integer, i.e. seconds), not a formatted date string.
As far as I know only comparison operators work on datetime objects ($date1 > $date2), not math operators ($date1 + $date2).
See also http://nl3.php.net/manual/en/datetime.add.php and http://nl3.php.net/manual/en/datetime.modify.php
Use 1 datetime instance for calculating/formatting the total amount of time
Or, convert 2 datetime instances to seconds, add them, and format using date()
The second parameter of date() is expected to be a Unix timestamp as integer, not a DateTime object. (see php.net)
You need to convert your DateTime object into a Unix timestamp.
Try getTimestamp():
echo date('H:i:s',$total->getTimestamp());
I have an application that needs to send a UTC timestamp in order for it to work correctly. In my application a user can have any number of timezones. So if they pick 3pm and their timezone is America/New_York, it is a different 3pm than if it was America/Chicago.
I need to figure out a way to change the date into the right UTC timestamp. I know I can use date_default_timezone_set("UTC")...but I don't think will work correctly.
I think I need to calculate a difference between UTC and regular timezone, but I am not sure. Any advice is welcomes.
date_default_timezone_set("UTC");
echo strtotime('5/13/2014 3:00 PM');
1399993200
date_default_timezone_set("America/New_York");
echo strtotime('5/13/2014 3:00 PM');
1400007600
As you can tell these 2 values are different.
EDIT: Here is what my code looks like. It doesn't seem to work correctly as the application doesn't show the event in the right time.
$previous_timezone = date_default_timezone_get();
date_default_timezone_set("UTC");
$aceroute_schedule = $this->sale_lib->get_send_to_aceroute_schedule();
if (($start_time = strtotime($aceroute_schedule['aceroute_schedule_date']. ' '.$aceroute_schedule['aceroute_schedule_time_start'])) !== FALSE)
{
//Append 000 as as string for 32 bit systems
$start_epoch = $start_time.'000';
$end_epoch = strtotime('+ '.$aceroute_schedule['aceroute_duration'].' minutes', $start_time).'000';
}
else //Default to current time + 1 hour
{
//Append 000 as as string for 32 bit systems
$start_epoch = time().'000';
$end_epoch = strtotime('+1 hour', time()).'000';
}
$event->start_epoch = $start_epoch;
$event->end_epoch = $end_epoch;
Update:
This will now create a DateTime object in the user's DateTimeZone ('America/New_York'). And then it will set that object's timezone to UTC. To get the timestamp (or other string representations of date), use ::format().
# Create NY date
$NY = new DateTimeZone("America/New_York");
$NYdate = new DateTime('5/13/2014 3:00 PM', $NY);
# Set timezone to UTC
$UTC = new DateTimeZone("UTC");
$UTCdate = $NYdate->setTimezone($UTC);
# Get timestamp (PHP 5.2 compatible)
$timezone = $UTCdate->format('U');
var_dump($timezone); // a string containing UNIX timestamp
First I create 2 DateTime objects based off of their respective DateTimeZone objects. Then we can either use OOP ::diff() to get another object containing information about the time difference. Or we can use simple integers representing the difference in seconds from ::getTimestamp.
$date = '5/13/2014 3:00 PM';
# Create NY date
$NY = new DateTimeZone("America/New_York");
$NYdate = new DateTime($date, $NY);
# Create UTC date
$UTC = new DateTimeZone("UTC");
$UTCdate = new DateTime($date, $UTC);
# Find difference object
$diff = $NYdate->diff($UTCdate);
var_dump($diff); // a DateInterval object containing time difference info
# Find difference in seconds
$diff = $NYdate->getTimestamp() - $UTCdate->getTimestamp();
var_dump($diff); // an integer containing time difference in seconds
Links:
DateTimeZone
DateTime
DateInterval
Example in http://www.php.net/manual/en/datetime.settimezone.php
$date = new DateTime('2000-01-01', new DateTimeZone('Pacific/Nauru'));
echo $date->format('Y-m-d H:i:sP') . "\n";
$date->setTimezone(new DateTimeZone('Pacific/Chatham'));
echo $date->format('Y-m-d H:i:sP') . "\n";
The first line creates a DateTIme object, using the timezone Pacific/Nauru.
You can then change the timezone using setTimezone as shown in line 4, and the output will be modified accordingly.
note: the default timezone (if you don't specify it in the 2nd parameter in line 1) is the one set in your php.ini file, which you can modify (at runtime) with date_default_timezone_set("America/New_York")
note2: the 1st parameter in line 1, is equivalent to the 1st parameter of the strtotime function.
note3: the format method takes the same format parameter as date (http://www.php.net/manual/en/function.date.php)
I have a PHP DateTime object with microseconds created as follows:
$time = microtime(true);
$microseconds = sprintf('%06d', ($time - floor($time)) * 1000000);
$dt = new DateTime(date('Y-m-d H:i:s.' . $microseconds, $time));
How can I modify the microseconds value of $dt, without creating a completely new DateTime instance?
You can't.
There are three methods that can modify the value of a DateTime instance: add, sub and modify. We can rule out add and sub immediately because they work in terms of a DateInterval which does not have sub-second precision.
modify accepts a string in one of the standard recognized formats. Of those formats, only the relative ones are of interest here because the other ones work in an absolute manner; and there is no relative format that allows tweaking the msec part (that unit is not recognized).
as of PHP 7.1
DateTime::setTime() supports microseconds.
This seems to have been available since 7.1.0-rc4
$dt = new DateTime('2020-01-01 0:00');
$dt->modify('+500 ms'); // Milliseconds.
$dt->modify('+123456 usec'); // Microseconds.
$dt->modify('+123456 microseconds'); // This works too.
It's mentioned here in the manual.
Manually creating a DateTime object with micro seconds:
$d = new DateTime("15-07-2014 18:30:00.111111");
Getting a DateTime object of the current time with microseconds:
$d = date_format(new DateTime(),'d-m-Y H:i:s').substr((string)microtime(), 1, 8);
Difference between two DateTime objects in microseconds (e.g. returns: 2.218939)
//Returns the difference, in seconds, between two datetime objects including
//the microseconds:
function mdiff($date1, $date2){
$date1sec = strtotime($date1->format('d-m-Y H:i:s.u'));
$date2sec = strtotime($date2->format('d-m-Y H:i:s.u'));
//Absolute val of Date 1 in seconds from (EPOCH Time) - Date 2 in seconds from (EPOCH Time)
$secdiff = abs($date1sec-$date2sec);
//Creates variables for the microseconds of date1 and date2
$micro1 = $date1->format("u");
$micro2 = $date2->format("u");
if (($date1sec<$date2sec && $micro1>$micro2)||($date1sec>$date2sec && $micro1<$micro2)){
$microdiff = abs(1000000 - abs($micro1-$micro2));
$secdiff = $secdiff - 1;
} else {
$microdiff = abs($micro1 - $micro2);
}
//Creates the variable that will hold the seconds (?):
$difference = $secdiff.".".$microdiff;
return $difference;
}
Essentially it finds the difference for the DateTime Objects using strtotime and then adding the extra microseconds on.
Do you need me to create add and sub?
i had a similar problem and ended up having to wrap the whole thing
https://gist.github.com/chandeeland/9817516
For the people only in need to zero-out microseconds (I had to because of database layer) here's the snippet I ended up using:
$format = "Y-m-d H:i:s e";
$now = (new \DateTime())->format($format);
$dateTime = \DateTime::createFromFormat($format, $now);
Note that using $format = 'c', ISO 8601, will not work, as explained here (https://stackoverflow.com/a/10478469/8119317).
I need to compare bentween a time taken from a database to the current time.
$DBtime = "2013-10-29 17:38:55";
this is the format of the arrays in the database.
How can I compare it with the current time?
Im not sure how, but maybe converting DBtime to Unixtime then:
(CurrentUnixTime - dbUnixTime) = x
Or maybe, we can take the 17:38 and compare it somehow with date("G:i");
Thank you! I hope you understand what I mean.
You can transform it into a UNIX timestamp using strtotime and then subtract the current timestamp by it.
$DBtime = "2013-10-29 17:38:55";
$db_timestamp = strtotime($DBtime);
$now = time();
$difference = $now - $db_timestamp;
echo $difference;
This will give you the difference in seconds.
You can convert the DBtime string to a unix timestamp in PHP using strtotime. In MySQL, you can use UNIX_TIMESTAMP when querying the column.
time() - strtotime($DBtime)
$date1 = new DateTime('2013-10-29 17:38:55');
$date2 = new DateTime('2013-11-29 18:28:21');
$diff = $date1->diff($date2);
echo $diff->format('%m month, %d days, %h hours, %i minutes');
$DBtime = "2013-10-29 17:38:55";
// Set whatever timezone was used to save the data originally
date_default_timezone_set('CST6CDT');
// Get the current date/time and format the same as your input date
$curdate=date("Y-m-d H:i:s", time());
if($DBtime == $curdate) {
// They match, do something
} else {
// They don't match
}
How to get millisecond between two DateTime objects?
$date = new DateTime();
$date2 = new DateTime("1990-08-07 08:44");
I tried to follow the comment below, but I got an error.
$stime = new DateTime($startTime->format("d-m-Y H:i:s"));
$etime = new DateTime($endTime->format("d-m-Y H:i:s"));
$millisec = $etime->getTimestamp() - $stime->getTimestamp();`
I get the error
Call to undefined method DateTime::getTimestamp()
In the strict sense, you can't.
It's because the smallest unit of time for the DateTime class is a second.
If you need a measurement containing milliseconds then use microtime()
Edit:
On the other hand if you simply want to get the interval in milliseconds between two ISO-8601 datetimes then one possible solution would be
function millisecsBetween($dateOne, $dateTwo, $abs = true) {
$func = $abs ? 'abs' : 'intval';
return $func(strtotime($dateOne) - strtotime($dateTwo)) * 1000;
}
Beware that by default the above function returns absolute difference. If you want to know whether the first date is earlier or not then set the third argument to false.
// Outputs 60000
echo millisecsBetween("2010-10-26 20:30", "2010-10-26 20:31");
// Outputs -60000 indicating that the first argument is an earlier date
echo millisecsBetween("2010-10-26 20:30", "2010-10-26 20:31", false);
On systems where the size of time datatype is 32 bits, such as Windows7 or earlier, millisecsBetween is only good for dates between 1970-01-01 00:00:00 and 2038-01-19 03:14:07 (see Year 2038 problem).
Sorry to digg out an old question, but I've found a way to get the milliseconds timestamp out of a DateTime object:
function dateTimeToMilliseconds(\DateTime $dateTime)
{
$secs = $dateTime->getTimestamp(); // Gets the seconds
$millisecs = $secs*1000; // Converted to milliseconds
$millisecs += $dateTime->format("u")/1000; // Microseconds converted to seconds
return $millisecs;
}
It requires however that your DateTime object contains the microseconds (u in the format):
$date_str = "20:46:00.588";
$date = DateTime::createFromFormat("H:i:s.u", $date_str);
This is working only since PHP 5.2 hence the microseconds support to DateTime has been added then.
With this function, your code would become the following :
$date_str = "1990-08-07 20:46:00.588";
$date1 = DateTime::createFromFormat("Y-m-d H:i:s.u", $date_str);
$msNow = (int)microtime(true)*1000;
echo $msNow - dateTimeToMilliseconds($date1);
DateTime supports microseconds since 5.2.2. This is mentioned in the documentation for the date function, but bears repeating here. You can create a DateTime with fractional seconds and retrieve that value using the 'u' format string.
<?php
// Instantiate a DateTime with microseconds.
$d = new DateTime('2011-01-01T15:03:01.012345Z');
// Output the microseconds.
echo $d->format('u'); // 012345
// Output the date with microseconds.
echo $d->format('Y-m-d\TH:i:s.u'); // 2011-01-01T15:03:01.012345
// Unix Format
echo "<br>d2: ". $d->format('U.u');
function get_data_unix_ms($data){
$d = new DateTime($data);
$new_data = $d->format('U.u');
return $new_data;
}
function get_date_diff_ms($date1, $date2)
{
$d1 = new DateTime($date1);
$new_d1 = $d1->format('U.u');
$d2 = new DateTime($date2);
$new_d2 = $d2->format('U.u');
$diff = abs($new_d1 - $new_d2);
return $diff;
}
https://www.php.net/manual/en/class.datetime.php
Here's a function to do that + tests.
https://gist.github.com/vudaltsov/0bb623b9e2817d6ce359eb88cfbf229d
DateTime dates are only stored as whole seconds. If you still need the number of milliseconds between two DateTime dates, then you can use getTimestamp() to get each time in seconds (then get the difference and turn it into milliseconds):
$seconds_diff = $date2.getTimestamp() - $date.getTimestamp()
$milliseconds_diff = $seconds_diff * 1000