Can anyone assist me as to why my seconds are not printing out correctly? The hours and minutes are both correct, but it is not printing out anything for the secs variable. The items in my arraylist are in System.currentTimeMillis(), which is why I have to convert them.
//divides 'logoutTimeTotal' by 'loginTimeTotal' to get 'totalTimeLoggedIn'
long totalTimeLoggedIn = (((totalTimeArray.get(1) - totalTimeArray.get(0)) / 1000) / 60);
//creates 2 variables that convert time logged in to hours and minutes
long hr = totalTimeLoggedIn / 60;
long min = totalTimeLoggedIn - (hr * 60);
long secs = totalTimeLoggedIn;
//creates String variable with hours and minutes logged in
String timeLoggedStr = hr + " Hours " + min + " Minutes " + secs + " Seconds";
Thanks
You problem is when you getting the totalTimeLoggedIn, you do:
long totalTimeLoggedIn = (((totalTimeArray.get(1) - totalTimeArray.get(0)) / 1000) / 60);
If you want to get the total time in second that generating using System.currentTimeMillis(), then you have to divide just on 1000,since the 1 second is 1000 milliseconds, so you need to do:
long totalTimeLoggedIn = (((totalTimeArray.get(1) - totalTimeArray.get(0)) / 1000));
It is probably caused by rounding.
Instead of long, using float is better.
Related
This question already has answers here:
Update time every second
(3 answers)
Closed 8 years ago.
I have been working on a code for an app but I cannot get the time to update in the emulator when I run the code. The code works in the compiler but not the emulator.
Any helpful suggestions would be greatly appreciated. The timer is a countdown to Christmas day.
Here is my code:
Calendar today = Calendar.getInstance();
Calendar thatDay = Calendar.getInstance();
thatDay.set(Calendar.DAY_OF_MONTH, 25);
thatDay.set(Calendar.MONTH, 11); // 0-11 so 1 less
thatDay.set(Calendar.YEAR, 2014);
thatDay.set(Calendar.HOUR, 0);
thatDay.set(Calendar.MINUTE, 0);
thatDay.set(Calendar.SECOND, 0);
thatDay.set(Calendar.AM_PM, 0);
System.out.println(thatDay.getTime());
ScheduledExecutorService scheduledExecutorService=
Executors.newScheduledThreadPool(1);
scheduledExecutorService.scheduleAtFixedRate(new ReadThisPeriod(thatDay), 0, 1,
TimeUnit.SECONDS);
long diff = (thatDay.getTimeInMillis() - today.getTimeInMillis()) / 1000;
long days = diff / (60 * 60 * 24);
long hours = diff / (60 * 60) % 24;
long minutes = diff / 60 % 60;
long seconds = diff % 60;
TextView daysBox = (TextView) findViewById(R.id.s1Days);
daysBox.setText(" + "" + days + "" + hours + "" + minutes + " " + seconds + " ");
Keeping things very simple, I'd remove all Executors stuff and do something like:
TextView daysBox = (TextView) findViewById(R.id.s1Days);
// We create a runnable that will re-call itself each second to update time
Runnable printDaysToXmas=new Runnable() {
#Override
public void run() {
Calendar today = Calendar.getInstance();
long diff = (thatDay.getTimeInMillis() - today.getTimeInMillis()) / 1000;
long days = diff / (60 * 60 * 24);
long hours = diff / (60 * 60) % 24;
long minutes = diff / 60 % 60;
long seconds = diff % 60;
daysBox.setText(" + "" + days + "" + hours + "" + minutes + " " + seconds + " ");
// we call this runnable again in 1000ms (1 sec)
daysBox.postDelayed(printDaysToXmas, 1000); // all views have a Handler you can use ;P
}
};
... and to start the process just do
printDaysToXmas.run();
... and to stop it, you can do
daysBox.removeCallbacks(printDaysToXmas);
Also some little add to rupps answer. You can use
DateUtils.getRelativeTimeSpanString(long time, long now, long minResolution);
to simplify math and give more user readable string for user.
Date lol = c.getTime();
long milli_now = lol.getTime();
c.set(2013, c.MAY, 21);
Date lol1 = c.getTime();
long milli_then = lol1.getTime();
long milli_tot = (milli_then - milli_now);
long sec = (milli_tot/1000);
long min = 0;
long hour = 0;
min = (sec/60);
days.setText("Days left: " + (sec/60/60/24));
countdown.setText(""+hour+":"+min+":"+sec);
What should I do to have it like 216 hours, 60 mins, 60 secs?
I can't figure out the algorithm.
Here is what you can do:
long totDiff = (lastDate.getTime() - firstDate.getTime()); // Total differance in milliseconds
long Sdiff = (totDiff / 1000) % 60; // Differance in seconds
long Mdiff = (totDiff / (60 * 1000)) %60; // Differance in minutes
long Hdiff = (totDiff / (60 * 60 * 1000)); // Remaining time in hours
This should give you the output you're looking for.
What are you getting with this code? As far as I can tell, the only thing you're missing is
hour = min / 60;
Currently I am printing my values for my swing worker timer in a label
.setText(days + " Days :" + hours + " Hours :" + mins + " Minutes : " + seconds + " Seconds elapsed")
I was wondering if it were possible to format this in a slightly neater way?
I've got a program that I'm working on now that uses String.format(...) and a format String for this:
// in the constants section
private static final String DISPLAY_FORMAT_STR = "%02d:%02d:%02d:%01d";
private void showTimeLeft() {
int oldMin = min;
hours = (int) (deltaTime / (MS_PER_SEC * SEC_PER_MIN * MIN_PER_HR));
min = (int) (deltaTime / (MS_PER_SEC * SEC_PER_MIN) % MIN_PER_HR);
sec = (int) (deltaTime / (MS_PER_SEC) % SEC_PER_MIN);
msec = (int) (deltaTime % MS_PER_SEC);
String displayString = String.format(DISPLAY_FORMAT_STR, hours, min, sec,
msec / 100);
displayField.setText(displayString);
// ... etc...
Otherwise if you're dealing with a Date object (I'm not), you could use a SimpleDateFormat object to better format your output.
How about String.format()?
http://docs.oracle.com/javase/6/docs/api/java/util/Formatter.html#syntax
One of ways, how do you can calculating elapsed time
long start = System.currentTimeMillis();
// some code executed
long end = System.currentTimeMillis();
long elapsed = end - start;
long seconds = elapsed / 1000;
rest for calculating days / hours / minutes / seconds
I am experiencing a problem with the code below. It's converting milliseconds to months, days, hours, and minutes.
long diffms = date2l - date1l; //The result here is in milliseconds; The value of date2l - date1l are different
long diff_minute = diffms / 60000;
long diff_hour = diff_minute / 60; float diff_minute_now = (diff_minute % 1) * 60; int dmn = (int) diff_minute_now;
long diff_day = diff_hour / 24; float diff_hour_now = (diff_hour % 1) * 24; int dhn = (int) diff_hour_now;
long diff_month = diff_day / 30; float diff_day_now = (diff_day % 1) * 30; int ddn = (int) diff_day_now;
diffe = new LabelField
("Remaining Time : " + Long.toString(diff_month) + " month(s) "
+ Integer.toString(ddn) + " day(s) "
+ Integer.toString(dhn) + " hour(s) "
+ Integer.toString(dmn) + " minute(s)");
add(diffe);
Why are the result values all zeroes?
EDIT:
#BicycleDude I modify your code into:
long diffms = date2l - date1l;
long ts = diffms / 1000;
long mo = ts / 60 / 60 / 24 / 30;
long d = (ts - mo * 30 * 24 * 60 * 60) / (60 * 60 * 24);
long h = (ts - d * 24 * 60 * 60) / (60 * 60);
long m = (ts - h * 60 * 60) / 60;
But the hours doesn't work
'anything % 1' will return 0. it's probably not what you intended.
The variables you divide initially are type long. So their results will also be long. (e.g. 12345 / 100 = 123 not 123.45).
The modulo operator works on remainder on division of integers. (e.g. 12345 % 100 = 45).
The algorithm you supplied doesn't extract day, month, hour, minute, second in the manner you expected. It requires rework before it's correct.
I've reworked the formulas with the assumption there are 31 days in a month:
long diffms = date2l - date1l;
long mo = (diffms / 1000 / 60 / 60 / 24 / 31);
long d = (diffms / 1000 / 60 / 60 / 24) % 31;
long h = (diffms / 1000 / 60 / 60) % 24;
long m = (diffms / 1000 / 60) % 60;
long s = (diffms / 1000) % 60;
I'm going to base my answer on the edited part of the code, since BicycleDude has already pointed out what was wrong with the modulo operations.
long diffms = date2l - date1l; //difference in ms
long ts = diffms / 1000; //total difference in seconds
long mo = ts / 60 / 60 / 24 / 30; //(1)
long d = (ts - mo * 30 * 24 * 60 * 60) / (60 * 60 * 24); //follows on because of (1)
long h = (ts - d * 24 * 60 * 60) / (60 * 60); //follows on because of (1)
long m = (ts - h * 60 * 60) / 60; //follows on because of (1)
Alright, I thought there would be multiple problems, but I think (think, I'm probably missing something...) that the main error is coming from your calculation of months, which I denoted in the code by the comment (1). You can't calculate the difference in months like that.
Why? What about if there was more than one month in differences? Wouldn't you need to divide by 31, instead? Or if it was a leap year? You'd need to divide by 29 if it was February. Since integer division doesn't round or account for decimals, you can get inaccuracies in your difference-in-months calculation. It's probably best if you instead use the differences in hours to calculate the difference in days, and from there you can figure out the difference in months. (Edit: I think you'd also need to take into account the factors I mentioned above when calculating the difference in months from the difference in days, by checking what your "origin" and "target" dates are, though I wouldn't be too sure of writing it myself at thie stage...)
Since you have a problem with the way you calculate the difference in months, and you use the erroneous value to calculate the difference in days, I think this results in the error propagating down to some of your other values (eg. the difference in hours).
EDIT
Okay, I mucked around with the code a bit more. As I noted earlier, your months calculation was dangerous and affected your days calculation, which potentially introduced errors later on.
With the example you provided in the comments, your code had a discrepancy of 3 days in the number of days. (The example was 19 January 2012 to 3 May 2012). I ran this against BicycleDude's code and it was fine.
I'll repost the code, and I've just added one line to find the number of days, based on how many hours have passed.
long h = ts / 60 / 60; // hour part
long m = (ts - h * 60 * 60) / 60; // minute part
long s = (ts - h * 60 * 60 - m * 60); // second part
long d = h / 24;
If you like to make it so that you can read that "there are w days, x hours, y minutes and z seconds between date2l and date1l", you could do something like this:
long date2l = Timestamp.valueOf("2012-05-03 05:30:10").getTime();
long date1l = Timestamp.valueOf("2012-01-19 00:00:00").getTime();
long diffms = date2l - date1l; //difference in ms
long diff_seconds = diffms / 1000; //total difference in seconds
long diff_mins = diff_seconds / 60; //total difference in minutes
long diff_hours = diff_mins / 60; //total difference in hours
long diff_days = diff_hours / 24; //total difference in days
long x = (diff_seconds - diff_days * 60 * 60 * 24) / (60 * 60);
long y = ((diff_seconds - (diff_hours * 60 * 60))) / 60;
long z = ((diff_seconds - (diff_mins * 60)));
long w = diff_days;
System.out.println(w + " " + x + " " + y + " " + z);
And it appears to work.
I haven't figured out the months part because that's a lot more non-trivial, but yeah. This kinda works?
The TimeUnit class provides factory methods that simplifies most of your work:
import static java.util.concurrent.TimeUnit.*;
// First, calculate the total difference in each unit
long diffDays = MILLISECONDS.toDays(diffMs);
long diffHours = MILLISECONDS.toHours(diffMs);
long diffMinutes = MILLISECONDS.toMinutes(diffMs);
long diffSeconds = MILLISECONDS.toSeconds(diffMs);
// Next, calculate the differences
long months = diffDays / 30;
long days = diffDays - 30 * months;
long hours = diffHours - DAYS.toHours(diffDays);
long minutes = diffMinutes - HOURS.toMinutes(diffHours);
long seconds = diffSeconds - MINUTES.toSeconds(diffMinutes);
How to convert System.currentTimeMillis(); to seconds?
long start6=System.currentTimeMillis();
System.out.println(counter.countPrimes(100000000)+" for "+start6);
The console shows me 5761455 for 1307816001290.
I can't read how many seconds that is.
Any help?
TimeUnit
Use the TimeUnit enum built into Java 5 and later.
long timeMillis = System.currentTimeMillis();
long timeSeconds = TimeUnit.MILLISECONDS.toSeconds(timeMillis);
long start = System.currentTimeMillis();
counter.countPrimes(1000000);
long end = System.currentTimeMillis();
System.out.println("Took : " + ((end - start) / 1000));
UPDATE
An even more accurate solution would be:
final long start = System.nanoTime();
counter.countPrimes(1000000);
final long end = System.nanoTime();
System.out.println("Took: " + ((end - start) / 1000000) + "ms");
System.out.println("Took: " + (end - start)/ 1000000000 + " seconds");
like so:
(int)(milliseconds / 1000)
Java 8 now provides the most concise method to get current Unix Timestamp:
Instant.now().getEpochSecond();
From your code it would appear that you are trying to measure how long a computation took (as opposed to trying to figure out what the current time is).
In that case, you need to call currentTimeMillis before and after the computation, take the difference, and divide the result by 1000 to convert milliseconds to seconds.
I have written the following code in my last assignment, it may help you:
// A method that converts the nano-seconds to Seconds-Minutes-Hours form
private static String formatTime(long nanoSeconds)
{
int hours, minutes, remainder, totalSecondsNoFraction;
double totalSeconds, seconds;
// Calculating hours, minutes and seconds
totalSeconds = (double) nanoSeconds / 1000000000.0;
String s = Double.toString(totalSeconds);
String [] arr = s.split("\\.");
totalSecondsNoFraction = Integer.parseInt(arr[0]);
hours = totalSecondsNoFraction / 3600;
remainder = totalSecondsNoFraction % 3600;
minutes = remainder / 60;
seconds = remainder % 60;
if(arr[1].contains("E")) seconds = Double.parseDouble("." + arr[1]);
else seconds += Double.parseDouble("." + arr[1]);
// Formatting the string that conatins hours, minutes and seconds
StringBuilder result = new StringBuilder(".");
String sep = "", nextSep = " and ";
if(seconds > 0)
{
result.insert(0, " seconds").insert(0, seconds);
sep = nextSep;
nextSep = ", ";
}
if(minutes > 0)
{
if(minutes > 1) result.insert(0, sep).insert(0, " minutes").insert(0, minutes);
else result.insert(0, sep).insert(0, " minute").insert(0, minutes);
sep = nextSep;
nextSep = ", ";
}
if(hours > 0)
{
if(hours > 1) result.insert(0, sep).insert(0, " hours").insert(0, hours);
else result.insert(0, sep).insert(0, " hour").insert(0, hours);
}
return result.toString();
}
Just convert nano-seconds to milli-seconds.
TimeUnit.SECONDS.convert(start6, TimeUnit.MILLISECONDS);
For conversion of milliseconds to seconds, since 1 second = 10³ milliseconds:
//here m will be in seconds
long m = System.currentTimeMillis()/1000;
//here m will be in minutes
long m = System.currentTimeMillis()/1000/60; //this will give in mins
// Convert millis to seconds. This can be simplified a bit,
// but I left it in this form for clarity.
long m = System.currentTimeMillis(); // that's our input
int s = Math.max(
.18 * (Math.toRadians(m)/Math.PI),
Math.pow( Math.E, Math.log(m)-Math.log(1000) )
);
System.out.println( "seconds: "+s );