How to keep the precision of datetime when taking into consideration time offsets

65 views (last 30 days)
I am writing a code that will convert the time into different readable (plotable) formats. For instance I have data that is reported in milliseconds, I would like to convert it to a 'HH:mm:ss.SSS' format. I am able to write code to do this. The issue is when I take into consideration a time offset, in a format 'HH:mm:ss.SSS', I lose the millisecond detail. Below is part of my code, I cannot share all of it.
if nargin < 4
pTimeOffsets = datetime('00:00:00.000',...
'Format','HH:mm:ss.SSS'); % this is the Time Offset, it is an optional argument and if left out is defaulted to nothing.
end
...
pConvertedTime = datetime(strcat(string(lHH),':',...
string(lmm),':',...
string(lss),'.',...
string(lSSS)),...
'Format','HH:mm:ss.SSS'); % this will take the milliseconds and convert into a datetime object.
%The desired precision is kept.
If I were to do this:
pConvertedTime = datetime(strcat(string(lHH),':',...%lHH is hour number
string(lmm),':',...%lmm is minute number
string(lss),'.',...%lss is second number
string(lSSS)),...%lSSS is millisecond number
'Format','HH:mm:ss.SSS') - pTimeOffsets; % offsets loses milliseconds precision
Any suggestions?
  2 Comments
John Steiner
John Steiner on 11 Dec 2019
Edited: John Steiner on 11 Dec 2019
Below is the working code exert, again I can't share the entire code for business reasons. Notice that pConvertedTime is saved in 'HH:mm:ss' format. If pConvertedTime does not take pTimeOffsets into consideration then the format is 'HH:mm:ss.SSS'.
pTimeInput = double([30102794;30102924;30103039;30103170;...
30103293;30103407;30103517;30103600;30103699;30103799]);
pTimeOffsets = datetime('00:00:00.000',...
'Format','HH:mm:ss.SSS');
lSSS = round(((pTimeInput/1000) - floor(pTimeInput/1000))*1000,0 );
lss = (pTimeInput - lSSS)/1000;
lHH = floor(lss/3600);
lmm = floor((lss/60) - lHH*60);
lss = floor( lss - (lmm*60) - (lHH*3600) );
pConvertedTime = datetime(strcat(string(lHH),':',...
string(lmm),':',...
string(lss),'.',...
string(lSSS)),...
'Format','HH:mm:ss.SSS') - pTimeOffsets;

Sign in to comment.

Accepted Answer

Steven Lord
Steven Lord on 11 Dec 2019
You don't actually want a datetime array, you want a duration array. That's easy. First remove the fractional seconds. There's no need to perform division, rounding, and multiplication for your lSSS.
lSSS2 = rem(pTimeInput, 1000);
The rest of your number is the number of seconds you want your duration to represent.
numSeconds = (pTimeInput-lSSS2)/1000;
Now build your duration.
d = seconds(numSeconds)+seconds(lSSS2)/1000
Because I built d using seconds it displays as seconds, but you can change its display Format. [This was, I believe, the main issue with your original code, but I find using seconds to be easier to explain than the arithmetic.]
d.Format = 'hh:mm:ss.SSS'
That looks to be in agreement with your pTimeInput data. Let's see them side-by-side to compare.
format longg
tt = timetable(d, pTimeInput)

More Answers (1)

John Steiner
John Steiner on 11 Dec 2019
I came up with a solution. I could not figure out how to modify datetime objects.
Instead of converting everything to datetime objects I converted into milliseconds performed the offset and then converted into datetime object.
The code is designed to output multiple different units and take in differnt units so there was some fluidity in how the code could be constructed. I initially used datetime as the midpoint as this is generally what will be the final result.
John

Categories

Find more on Dates and Time in Help Center and File Exchange

Products


Release

R2019b

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!