Get Time Difference without if else statement - c

C Time Difference
scanf ("%2d %2d", &shours, &sminutes);
printf ("Enter End Time : ");
scanf ("%2d %2d", &ehours, &eminutes);
printf ("\nTIME DIFFERENCE\n");
tohours = ehours - shours;
printf("Hour(s) : %2d", tohours);
tominute = eminutes - sminutes;
printf("\nMinute(s): %2d ", tominute);
How can I make my output like this? When I try to run my code the minutes output is -59 instead of 1 and my hours is the one who got the output "1"
P.S. without using the if else statements

Use (some sort of) timestamps, by turning your hours and minutes variables into one, e.g:
stime = shours * 60 + sminutes;
etime = ehours * 60 + eminutes;
then calculate de difference of that
totime = etime - stime;
then convert that back into hours and minutes
tominutes = totime % 60;
tohours = (totime - tominutes) / 60;
(integer division will take care of rounding down)
Not the most elaborated solution, but I guess you're looking for an beginners-friendly solution
Edit
speaking of beginner-friendly: the % is the modulus operator that returns the remainder of a division. So when you divide 119 by 60 it returns 59. And yes, you could also just get the hours from dividing totime by 60 and let the integer division do the job, but it's nicer (read: clearer to read what's going on) when you divide (totime - tominutes) because it's like the missing part to the line with the modulus

Related

GMT subtraction on MATLAB

I'm currently working on a small project on handling time difference on MATLAB. I have two input files; Time_in and Time_out. The two files contain arrays of time in the format e.g 2315 (GMT - Hours and Minute)
I've read both Time_in' and 'Time_out on MATLAB but I don't know how to perform the subtraction. Also, I want the corresponding answers to be in minutes domain only e.g (2hrs 30mins = 150minutes)
this is one of several possible solutions:
First, you should convert your time strings to a MATLAB serial date number. If you've done this, you can do your calculation as you want:
% input time as string
time_in = '2115';
time_out = '2345';
% read the input time as datenum
dTime_in = datenum(time_in,'HHMM');
dTime_out = datenum(time_out,'HHMM');
% subtract to get the time difference
timeDiff = abs(dTime_out - dTime_in);
% Get the minutes of the time difference
timeout = timeDiff * 24 * 60;
Furthermore, to calculate the time differences correctly you also should put some information about the date in your time vector, in order to calculate the correct time around midnight.
If you need further information about the function datenum you should read the following part of the MATLAB documentation:
https://de.mathworks.com/help/matlab/ref/datenum.html
Any questions?
In a recent version of MATLAB, you could use textscan together with datetime and duration data types to do this.
% read the first file
fh1 = fopen('Time_in');
d1 = textscan(fh1, '%{HHmm}D');
fclose(fh1);
fh2 = fopen('Time_out');
d2 = textscan(fh2, '%{HHmm}D');
fclose(fh2);
Note the format specifier '%{HHmm}D' tells MATLAB to read the 4-digit string into a datetime array.
d1 and d2 are now cell arrays where the only element is a datetime vector. You can subtract these, and then use the minutes function to find the number of minutes.
result = minutes(d2{1} - d1{1})

Adding 0 at starting of int value in c

I am in WinCE7 and to get the current time, I am using GetLocalTime(&systemTime);. This function gives the value of current time. Now if the milliseconds is 81, it displays it as 81 due to which the error occurs when I subtract two time values. For ex: time1 : 12:34:13:851 & time2: 12:34:14:81. Now I need to subtract seconds and milliseconds. So using sprintf, I am extracting seconds and milliseconds and putting them in time1 & time2 :
sprintf(time1,"%d.%d",systemTime.wSeconds,systemTime.wMilliseconds)
sprintf(time2,"%d.%d",systemTime.wSeconds,systemTime.wMilliseconds)
I am converting time1 & time2 into float using atof.Now time1 is 13.851 and time2 is 14.81. The milliseconds of time2 is actually 081 but it displays 81 so while subtracting it consider it as 810 which gives wrong values.
time2--> 14.810 14.081
time1--> 13.851 13.851
-------- ---------
result 0.959(wrong) 0.23(correct)
So to remove this error I thought of counting the digits of milliseconds and if it is 2 then add 0 at starting. So I did:
double digits = (floor (log10 (abs (milliseconds))) + 1); //calculate digits
if(digits == 2) //if milliseconds contains 2 digits, we need to add 0 at starting
{
sprintf(newMS,"0%d",milliseconds); //adding 0 to milliseconds
finalMilliseconds = atoi(newMS); //newMS is in char so converting it into integer and storing the value in finalMilliseconds
}
The problem occurs here. Lets say milliseconds = 18, so newMS = 018 but finalMilliseconds is again 18.
Please suggest any other way of conversion or any other way of adding 0 at starting
According to the documentation of SYSTEMTIME from MSDN:
It is not recommended that you add and subtract values from the
SYSTEMTIME structure to obtain relative times. Instead, you should
Convert the SYSTEMTIME structure to a FILETIME structure.
Copy the resulting FILETIME structure to a ULARGE_INTEGER structure.
Use normal 64-bit arithmetic on the ULARGE_INTEGER value.
The example here will give you some idea on how to get started.
It seems to me the simplest solution is to borrow what you need.
You already have integers. If you're subtracting two systemTime values, t2 from t1, say,
if( t1.wMilliseconds < t2.wMilliseconds ) {
t1.wMilliseconds += 1000;
t1.wSeconds--;
}
Or, just perform the subtraction. If the result's wMlliseconds is negative, adjust as above.
Take care to ensure t1 > t2, though. You don't want -1.25 = 0.0 - 0.75.
Instead of putzing with strings, if you want a float, make one:
double time1 = t1.wSeconds + 0.001 * t1.wMilliseconds;
C does the conversion for you. It's faster, more direct, and less error-prone than going through strings.
Another way of dealing with these marvels of lost leading or trailing zeroes (found in time and longlat), is to right pad the string with say four zeroes .i.e your newMS+"0000", and take the leftmost four characters.
You then have a number (as text) ranging from "0000" to "9990".
Put a "1" in front of it, then you can easily and unambiguously convert to an integer between 10000 and 19990.
Then you can add and subtract as you like.
Clumsy? Yes indeed :) But I have had to do weird tricks like this when GPS longitude readings go from 11.59(funny numbers) to 12.00

Converting days since Jan.1 1900 to today's date

typedef struct dbdatetime
{ // Internal representation of DATETIME data type
LONG dtdays; // No of days since Jan-1-1900 (maybe negative)
ULONG dttime; // No. of 300 hundredths of a second since midnight
} DBDATETIME;
I am trying to convert this struct into today's date. I don't suspect the time will give me much trouble but I am having problems with the logic of converting the total number of days to the proper month and day.
Ex. Friday November 7th is 41948 days.
You can divide by 365.2425+1900 to get the current year but how would you get the proper month / date.
Does C have anything built in to handle this? I am not a C programmer by trade.
There's nothing in the C standard directly to handle this, but if you are willing to write OS specific code, or can import libraries like boost::date_time, this is the best option. Don't attempt to handle it yourself unless you are okay with edge cases being wrong. Dates and times are notoriously difficult to get right.
Here are the docs for date_time which can do arithmetic on dates, including "add N days to 1/1/1900". http://www.boost.org/doc/libs/1_56_0/doc/html/date_time/gregorian.html#date_time.gregorian.date_duration
date d(1900, Jan, 1)
d += days(dtdays);
EDIT: OP can't use boost, but I'll leave this here in case a future visitor could use the info.
As you said, you can divide the number of days by 365.2425 to get a approx estimation of the year. Once you have that, use the number of years and leap years between 1900 and that year to calculate the number of days till that year.
You need to make sure that the logic for detecting leap years is sound. Once you know which years are leap years, you'll be fine. For example, 1900 is NOT a leap year, even though it is divisible by 4. Google leap year rules to find out why.
Once you have that, the remaining days will belong to the current year. Use the leap year logic again to determine whether you the current year is leap or not. Then on it's just a matter of counting days for each month.
C++ is out of the question, thanks for all the input guys.
I did find this algorithm that seems to work so far but am testing it now.
int l = nSerialDate + 68569 + 2415019;
int n = int(( 4 * l ) / 146097);
l = l - int(( 146097 * n + 3 ) / 4);
int i = int(( 4000 * ( l + 1 ) ) / 1461001);
l = l - int(( 1461 * i ) / 4) + 31;
int j = int(( 80 * l ) / 2447);
nDay = l - int(( 2447 * j ) / 80);
l = int(j / 11);
nMonth = j + 2 - ( 12 * l );
nYear = 100 * ( n - 49 ) + i + l;
Trying to find some theory behind it now.
Thanks for all of the input everyone, here is what I ended up doing.
Convert dtdays to seconds, minus the offset of the number of seconds between Jan-1-1900(Serial Date) and Jan-1-1970(UNIX Time). Which is 2208988800, this leaves us with UNIX time.
Convert the hundredths of seconds into seconds and add to the total.
Convert UNIX time using gmtime() to a tm struct.

Given an integer time in the format hhmmss how can it be formatted to hh:mm:ss

I am trying to split a timestamp in C into a suitable format, this format is to be hh:mm:ss.
The timestamp is stored as a positive integer in the format hhmmss. Is there a way to format this in C?
I have no code to show as I have no idea where to start really, my idea is store the timestamp in a character array, then every 2 characters print a ':' character.
Example output:
timestamp = 123456
I want it shown as 12:34:56
timestamp = 010203
I want it shown as 01:02:03
int timestamp = 10203;
int hour = timestamp / 10000;
int minute = timestamp % 10000 / 100;
int second = timestamp % 100;
printf("%02d:%02d:%02d\n", hour, minute, second);
Be careful when the timestamp starts with 0, because 010203 is an octet integer literal, the result may not be what you expected.
You can use integer division to split the number up how you like.
For example, to get the seconds you could do
seconds = timestamp % 100
And to get the minutes you could
minutes = (timestamp / 100) % 100
Then you can use printf to print out the time in any format you like.
e.g.
printf("%02d:%02d", minutes, seconds);

In c , how do I make 1200 / 500 = 3

In C , how do I make 1200 / 500 = 3.
I'm doing a homework assignment.
Shipping Calculator: Speedy Shipping company will ship your package based on how much it weighs and how far you are sending the package. They will only ship small packages up to 10 pounds. You need to have a program that will help you determine how much they will charge. The charges are based on each 500 miles shipped. They are not pro-rated, i.e., 600 miles is the same charge as 900 miles.
Here is the table they gave you:
Package Weight--------------------------Rate per 500 miles shipped
2 pounds or less------------------------$1.50
More than 2 but not more than 6---------$3.70
More than 6 but not more than 10--------$5.25
Here is one test case.
Test Case Data:
Weight: 5.6 pounds
Miles: 1200 miles
Expected results:
Your shipping charge is $11.10
My answer keeps coming out to 7.40
Are you trying to round up? Before dividing, you could add 499 to the number that is being divided.
(0 + 499) / 500 -> 0
(1 + 499) / 500 -> 1
(1200 + 499) / 500 -> 3
This will round up.
Say you want to get a ceiling division a by b (in your example a = 1200 b = 500).
You can do it in integer arithmetic like this.
result = (a + b - 1) / b;
Or you could use floating point numbers and do it like this (probably a bad idea)
result = (int) ceil( (double) a / b );
The thing is that as this is a homework, you could just make it up in small steps:
if( a % b == 0 ) {
result = a / b;
} else {
result = a / b + 1;
}
Another advantage of this code is that it actually doesn't overflow for too big as, but this is not relevant in this case, I guess.
I'd suggest using the mod and truncate functions. If mod comes out zero, it's fine, otherwise truncate and add 1.
You have to use the ceiling of the division. This will round the quotient up to the next integer.
So when you are trying to find the number of 500-mile increments, you have to round the quotient up to the next integer.
Alternatively, (and inefficiently), you could increment the number of miles by 1, until it is divisible by 500...that is, while ( (q = x_miles++%500) != 0 ) {} . Then multipy q by the rate to get your answer (That is also assuming you will have an integer number of miles).
You could also use the stdlib div function. This might be nice if you only wanted integer math and specifically wanted to avoid floating point math.
http://www.cplusplus.com/reference/clibrary/cstdlib/div/
#include <stdlib.h>
int foo(void)
{
div_t result = div(1200, 500);
return result.quot + (0 < result.rem);
}
[EDIT1]
From your code you would implement this part as follows:
if ( weight <= 5.6 )
{
int multiplier = (int) miles / 500;
if( ((int)miles % 500) > 0)
multiplier++;
rate370 = (double)multiplier * 3.7;
printf("Your total cost : %.2lf\n", rate370);
}
[ORIGINAL]
In "integer land" 1200 / 3 should equal to 2.
for what it "seems" you want try this:
int multFiveHundreds = (int)totalWeight / 500;
if(multFiveHundreds % 500 > 0)
multFiveHundreds++;

Resources