Help - Search - Members - Calendar
Full Version: EPOCH time - subtracting
Invision Power Services > Community Forums > Community Web Design and Coding
Watty
Does anyone know if it's possible to subtract EPOCH time?

For instance:

1144691356 - 1144691290 = 66

I then want to convert 66 to display in human readable form (i.e. date("h:i");
Stephen
Am I missing something? You've just answered your own question :|

Then just pass the resulting time stamp in the second parameter of date() (string date ( string format [, int timestamp] ))
Brendon Koz
Although this technically will work, it's also going to think you're talking about January 1970 if you use date() with those parameters.

Although usually inadvisable (for larger computations), I think using mathematical logic would be better...

CODE
$seconds = 1144691356 - 1144691290;    //replace with timestamp variables if any
$minutes = $seconds / 60;
$hours   = $minutes / 60;
$minutes = $minutes % 60;     //resets minutes after we get hours
$seconds = $seconds % 60;     //resets seconds after we get minutes

// ^ I think the above math is correct...just woke up.  :P
_
I haven't tested yours, but in case that doesn't work, here's one I've used:
CODE
$diff = $then - $now;

if($diff < 0)
{
        $diff = 0;
}

$days = floor($diff / 60 / 60 / 24);
$hours = floor(($diff - $days * 60 * 60 * 24) / 60 / 60);
$minutes = floor(($diff - $days * 60 * 60 * 24 - $hours * 60 * 60) / 60);
$seconds = floor($diff - $days * 60 * 60 * 24 - $hours * 60 * 60 - $minutes * 60);


(looks inefficient, dunnit? tongue.gif )
Brendon Koz
Note: I should have used "floor" or "intval" functions in my code...I forgot from my C++ days that PHP doesn't typecast back to an integer. biggrin.gif

As far as Veracon's code, it would be better to use constants over the continuous math (i.e.: define('SECS_IN_DAY', 60*60*24)).
Watty
I'm just not a programmer - plain and simple.

CODE
$seconds = $row['t22'] - $row['t11'];    //replace with timestamp variables if any
$minutes = $seconds / 60;
$hours   = $minutes / 60;
$minutes = $minutes % 60;     //resets minutes after we get hours
$seconds = $seconds % 60;     //resets seconds after we get minutes


I've come close to the above - but as usual, it keeps returning "0" as the result.

I should just save face and buy the company a physical time clock. devil.gif
_
QUOTE(malikyte @ Apr 11 2006, 07:56 AM) *
Note: I should have used "floor" or "intval" functions in my code...I forgot from my C++ days that PHP doesn't typecast back to an integer. biggrin.gif

Be glad you don't code in Python. fear.gif That's even "worse" (though it's really a favour as it reminds you to code properly).

QUOTE(malikyte @ Apr 11 2006, 07:56 AM) *
As far as Veracon's code, it would be better to use constants over the continuous math (i.e.: define('SECS_IN_DAY', 60*60*24)).

Yeah, as I said, it's not very efficient. ermm.gif

Watty: Are you sure the two variables you're subtracting are integers (and not just strings containing numbers)?
Stephen
Ah right I see what you want now; thought I was missing something.
Brendon Koz
QUOTE(Veracon @ Apr 11 2006, 12:08 PM) *
Watty: Are you sure the two variables you're subtracting are integers (and not just strings containing numbers)?

If that's the case, try encapsulating the two numbers you're working with using intval(), and then doing the math.


Watty, I'd be more than happy to get a working version for you. Just say the word, and your new requirements. original.gif
Watty
QUOTE(Veracon @ Apr 11 2006, 12:08 PM) *
Be glad you don't code in Python. fear.gif That's even "worse" (though it's really a favour as it reminds you to code properly).
Yeah, as I said, it's not very efficient. ermm.gif

Watty: Are you sure the two variables you're subtracting are integers (and not just strings containing numbers)?


Yea, they are entered into the DB as MySQL field INT. Fields t22 and t11. If I plug in the actual epoch time, then it (nearly) works: 1.23388888889:14 But plugging in epoch times obviously isn't practical. sad.gif
Stephen
Can you not have the two fields as MySQL timestamps or datetime fields? Then you can use something like

SQL
SELECT DATE_FORMAT(TIMEDIFF(t22, t11), '%h:%m %s') AS time FROM table


instead of having to get the fields and then calculate the difference and convert it to a human readable format

To enter the values into the field you would just need to do

SQL
INSERT INTO table (t11) VALUES(NOW())


rather than having to work it out yourself
Brendon Koz
...and if you did want to work something out yourself, you can convert back from MySQL date times to a UNIX timestamp by using the UNIX_TIMESTAMP() function within MySQL:

SELECT UNIX_TIMESTAMP(t11) AS time FROM timecard [...]
Rikki
I don't get why you're doing a modulus at the end of that code... Maybe I'm missing something. Try it without these lines:

QUOTE
$minutes = $minutes % 60; //resets minutes after we get hours
$seconds = $seconds % 60; //resets seconds after we get minutes


Then you can round it up or down to get a full integer.
Watty
I really appreciate you guys helping out with this. With each reply, I look at what was posted and it triggers something in my peanut brain. original.gif

Anyway - I thought I'd give MySQL's DateTime a shot and really thought I had it finally nailed. Yea right. I TOTALLY thought this would work:

CODE
$t22=date("Y-m-d H:i:s");


$sql = "UPDATE timesheet SET t2='$t2', t22='$t22' WHERE userid='$userid' AND t2 = ''";
$result = mysql_query($sql);


$timeIn = $row['t11'];
$timeOutToLunch = $row['t22'];
echo "Time In: ". $timeIn;
echo "Time Out to Lunch: ". $timeOutToLunch;
echo "Hours: ". date("H:i:s", (strtotime($timeOutToLunch) - strtotime($timeIn));


However, when it processes - I get a parse error: Parse error: parse error, unexpected ';' in C:\apache2triad\htdocs\timesheet\otl.php . The error is for the last chunk of code. What in the WIDE WIDE WORLD OF SPORTS am I missing?
Brendon Koz
QUOTE(Watty @ Apr 11 2006, 07:08 PM) *
CODE
echo "Hours: ". date("H:i:s", (strtotime($timeOutToLunch) - strtotime($timeIn)));

From my count, you were missing a closing parenthesis.
Watty
Brendon, Brendon, Brendon.... thumbsup.gif

Sometimes I guess I look TOOOOO hard instead of for the obvious/easy stuff.
Dagur
QUOTE(Veracon @ Apr 11 2006, 07:08 PM) *
Be glad you don't code in Python. fear.gif That's even "worse" (though it's really a favour as it reminds you to code properly).


In python you would use datetime objects so this wouldn't be a problem to begin with.
Watty
Crazy - no matter what values I have in t11 and/or t22, it returns: 16:00:00
_
QUOTE(Dagur @ Apr 12 2006, 01:45 AM) *
In python you would use datetime objects so this wouldn't be a problem to begin with.

Indeed, but that's not really what I meant; more in general, Python is more strongly typed. tongue.gif
Brendon Koz
Watty, even after looking over your code, I had to do the parenthesis counting check. First, count all parenthesis (and/or brackets, depending on your situation) that are open '('. Then count the comparable parenthesis that are closed ')'. If they don't match up (i.e.: 3v4), you're missing one. After I fixed it, I still thought it looked funny and had to double check myself. wink.gif

As for your math, output the variables in a mathematical equation form. If you're doing the math within MySQL, use a SELECT query instead, get the variables, and do the math (if possible - if not, select the fields and output them to see what form they're in).

Sometimes it helps to see, visually, the math you're doing.

i.e.:
Original: echo $variable1 - $variable2;
Convert to: echo $variable1, ' - ', $variable2, ' = ', ($variable1-$variable2);

...or if you have a more capable PHP IDE to work with, you can follow the stack, as it does this for you. original.gif
Watty
Yea, I think that's part of the problem...

I have $timeIn = $row['t11']; which is the db field holding the clockin value (int - timestamp).

then when I echo it, nothing comes up - so I'm missing something.
Brendon Koz
Sounds like either there's nothing in the database (that sounds odd, eh?) or your computational (programming) logic is a bit silly somewhere in there.

When that happens, and you don't have a capable IDE (such as Zend, Komodo, PHP IDE, or a couple others) that show you values of your variables while doing a code walkthrough, then you have to do the annoying "echo $this; echo $that; echo 'old mcdonald had a farm';" until you can find the error in your ways. Using " [...] or die('Uh oh!');" sometimes works too, especially for database queries.

If you think phpMyAdmin is a bit too cumbersome for querying the database and taking a slightly more serious look at the inner workings of the database, may I suggest a GUI based one? Either MySQL AB's Query Browser or Webyog's SQLyog ( http://www.webyog.com/ - Free version, more powerful than MySQL's solution). I use SQLyog, personally, even though I have all of MySQL AB's tools downloaded, and a couple others. The nice thing about using a GUI is you can echo out your SQL command from PHP, copy that from the resulting PHP page right into the query window of your sql manager and run the query to see what the results *should* be.

Anyway, enough of my marketing advertisement for a GUI-based MySQL software tool. biggrin.gif

You're basically going to have to echo out almost every variable from here to the moon, even your result resources just to be sure there's something there (echo '<pre>',print_r($variable),'</pre>';).
elj
That's the best way to bugcheck - echo out everything and use die() liberally. Also, on your MySQL queries, I usually use something like (for bugchecking):

CODE
$sql = "SELECT * FROM table";
$query = mysql_query($sql) or die("SQL: " . $sql . "<br />Error: " . mysql_error());
Brendon Koz
...just make sure you remove those errors when you're done bug checking so that any angry employees that might eventually use the script won't see your database connection information if something does in fact go wrong. original.gif

$query = @mysql_query([...]);

Just remember that if something does go wrong and you start getting blank pages and nothing being output, it's probably because of a blank die() or an error supression on a query. (Which is why people code error handling methods and functions, but I think you're more worried about getting it to work than the functionality.)
Watty
I'm making *some* headway.

I'm back to have the DB fields as INT.
I'm entering data into those 2 fields with time();

I'm able to subtract the 2 fields and display the difference using:
CODE
$difference = $row['t22'] - $row['t11'];
echo $difference;


So for instance: Clock In time = 1144943126
Out to lunch time = 1144953583

After the above is run, the result displayed is: 10457

Where I'm stuck now is changing/converting the result to display as human readable time. blink.gif
_
Alright, here's a little function:
CODE
function secs_to_hms($seconds)
{
    return array(intval(intval($seconds) / 3600), intval(($seconds / 60) % 60), intval($seconds % 60));
}


Returns array(hours, minutes, seconds). If you need any more than that, you can use the method I posted earlier.

(GOD, a real lambda implementation could've simplified this function.)
Watty
SOOOO close!

CODE
$sql2 = "UPDATE timesheet SET total_hours = (TIMEDIFF(lunch,clockin)) WHERE userid = '$userid'";
$result = mysql_query($sql2);


The above actually returns the correct difference in HOURS... however, it doesn't return any minutes.



I've also produced another problem... if the lunch time goes past 12pm (i.e. 1 or 2) and the clockin time is before 12 - then nothing is returned. Should I change it to a 24 hour datetime versus the standard american 12 hour datetime?

**EDIT
Got the first issue resolved - changed the total_hours from an unsigned INT to a TIME field. Going to play with the 24 hour clock now to see if that fixes problem 2.

**EDIT2
24 hour clock fixed it!

I guess sometimes it helps to post your problem so you can visually "see" it in order to get the dead mass between your ears to activate.
Watty
Ok, so I've got the morning time and afternoon time(s) down. They clock in for the day, they clock out for lunch. Both times are saved to the DB and I use mysql's timediff to compute the hours worked for the morning and this is stored into the db as TIME.

Then they clock in from lunch, clock out for the day. Same process as above... afternoon hours are recorded and the hours worked for the afternoon are recorded into the DB as TIME.

Now I'm stuck with adding up the mornings total hours to the afternoons morning hours for a daily total hours.

I was hoping it was as simple as

CODE
$sql4 = "UPDATE timesheet SET daily_hours = (TIMEDIFF(lunch,clockin) + (TIMEDIFF(clockout, back_lunch))) WHERE userid = '$userid'";
$result = mysql_query($sql4);


Anyone have a suggestion or two? unsure.gif
Brendon Koz
You won't like my suggestion:
You're doing too much with a database. Databases are used to store data, not information. You're doing both. You're storing the data (clock in, clock out) times, and then creating information (hours worked, daily hours). So...

What happens when your boss wants a monthly or tri-monthly report? Can you easily tweak your code to do this? Doubtfully. Use the dynamic language to its best ability. Veracon posted a function you could use to get the hours/minutes/seconds in the form of an array when using UNIX timestamp values. Gathering data from certain date ranges are easy in MySQL...you can then add up all the differences and there's your hours worked. With your current configuration, you're making more work for yourself AND creating more bloat to the database than necessary.

HOWEVER, continuing on your current path (since you want to get it done), I think I'd have to see your table structure. You might want another WHERE clause to specify the date, unless you plan on adding up all morning/afternoon fields for a certain user.

P.S. - Happy Easter. original.gif
Watty
Oh I agree completely... but due to the lack of knowledge I have with programming something/anything from scratch, I'm basically following the path of least resistance for now. There will only be, for now, 5 users of this script. At this point, I'm not overly concerned with the total hours for the day since I have their morning hours and afternoon hours. I did call the boss man today and told him that all I'll have for Monday is the ability for employees to create their account and then log their times.

There's still a TON of functionality that I need to do. An entire admin side (I'll have to throw something basic together tonight which will allow him to view/edit users times if need be). On top of that, I'll need to figure out some sort of array function in order to have "pay periods" available so that it can be more easily handled for sorting/gathering/processing, etc. Not anything I'm really looking forward to - but I started it and I'm determined to finish it.

I very nearly gave up completely Friday night/Saturday morning and actually found a Windows/stand alone based timecard solution that basically does everything we need it to do. And it only costs $24.95 for 200 users!

My eyes are already dropping on me as it's been a LONG Easter weekend - non-stop... but I have to tredge forward to finish what I can this evening.

Happy Easter to you as well! thumbsup.gif
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Invision Power Board © 2001-2009 Invision Power Services, Inc.