I have the following method to sum time:
public static String sumTime(String date1, String date2) throws ParseException {
Calendar calendar = Calendar.getInstance();
SimpleDateFormat formatter = new SimpleDateFormat("HH:mm:ss.SSS");
Date d1 = formatter.parse(date1);
Date d2 = formatter.parse(date2);
calendar.setTime(d2);
d1 = DateUtils.addHours(d1, calendar.get(Calendar.HOUR_OF_DAY));
d1 = DateUtils.addMinutes(d1, calendar.get(Calendar.MINUTE));
d1 = DateUtils.addSeconds(d1, calendar.get(Calendar.SECOND));
d1 = DateUtils.addMilliseconds(d1, calendar.get(Calendar.MILLISECOND));
return formatter.format(d1);
}
DateUtils is from Apache Commons Lang 3
It works quite well for what I want, unless the sum is bigger than 24 hours.
For example:
String time = "00:00:00.000";
try {
for (int i = 0; i < 24; i++) {
time = sumTime(time, "01:00:00.123");
}
System.out.println(time);
} catch (ParseException e) {
e.printStackTrace();
}
The result is:
00:00:02.952
But this is what I'd like it to be:
24:00:02.952
Is there any (easy) way to accomplish that?
I don't mind using different libraries/methods, as long as I get the correct result.
Keep in mind that time will always start in 00:00:00.000;
Have you thought about using days to represent each set of 24 hours? You could add something in your sumTime method, and have it add days. SimpleDateFormater can use days, maybe this will help:
http://docs.oracle.com/javase/6/docs/api/java/text/SimpleDateFormat.html
java.util.Date is not so strong in this area. See the Joda Time for a library that handles this properly.
I don't have access to an installation just now. The code will be close to this:
DateTimeFormatter dtf = DateTimeFormat.forPattern("HH:mm:ss.SSS");
DateTime start = dtf.parseDateTime(date1);
DateTime end = dtf.parseDateTime(date2);
PeriodFormatter pf = new PeriodFormatterBuilder()
.printZeroAlways().appendHours().appendSeparator(":")
.appendMinutes().appendSeparator(":")
.appendSeconds().appendSeparator(":")
.appendMillis3Digit().toFormatter();
return pf.print(new Period(start, end, PeriodType.time()));
Date is not the right thing class to use. Date is a instant of time, not a "Date Difference".
The right thing to do will be to use a library like Joda Time as someone has already suggested. If you don't want to do so - here's a possible alternative:
Parse the string into hours, minutes and seconds yourself, and then add it yourself.
I would encourage you to look into a "well accepted" library though. There may be things I'm not thinking of in my solution. Also, you have add all the error checking.
Here's the starter code:
public class TimeInterval {
short milliSeconds;
short seconds;
short minutes;
int hours;
public TimeInterval (String dateString) {
// HHHHHH:MI:SS.SSS
Pattern pattern = Pattern.compile("(\\d+):(\\d\\d):(\\d\\d)\\.(\\d\\d\\d)");
Matcher matcher = pattern.matcher(dateString);
if ( matcher.find() ) {
hours = Integer.parseInt(dateString.substring(matcher.start(1), matcher.end(1)));
minutes = Short.parseShort(dateString.substring(matcher.start(2), matcher.end(2)));
seconds = Short.parseShort(dateString.substring(matcher.start(3), matcher.end(3)));
milliSeconds = Short.parseShort(dateString.substring(matcher.start(4), matcher.end(4)));
}
}
private TimeInterval() {
}
public TimeInterval add(TimeInterval interval) {
TimeInterval ret = new TimeInterval();
ret.milliSeconds = (short) ((interval.milliSeconds + milliSeconds)%1000);
int carry = (interval.milliSeconds + milliSeconds)/1000;
ret.seconds = (short) ((interval.seconds + seconds)%60 + carry );
carry =(interval.seconds + seconds)/60;
ret.minutes = (short) ((interval.minutes + minutes)%60 + carry);
carry = (interval.minutes + minutes)/60;
ret.hours = (interval.hours + hours + carry);
return ret;
}
#Override
public String toString() {
return String.format("%d:%02d:%02d.%03d", hours, minutes, seconds, milliSeconds);
}
}
Using this class your program will be like :
TimeInterval time = new TimeInterval("00:00:00.000");
try {
for (int i = 0; i < 24; i++) {
time = time.add(new TimeInterval("01:00:00.123"));
}
System.out.println(time.toString());
} catch (ParseException e) {
e.printStackTrace();
}
Have you tried Joda-Time which actually has direct support for this sort of thing?
PeriodFormatterBuilder builder = new PeriodFormatterBuilder();
builder.printZeroAlways()
.minimumPrintedDigits(2)
.appendHours()
.appendSeparator(":").appendMinutes()
.appendSeparator(":").appendSeconds()
.appendSeparator(".").appendMillis3Digit();
PeriodFormatter formatter = builder.toFormatter();
PeriodParser parser = builder.toParser();
String s1 = "11:00:00.111";
String s2 = "23:00:00.111";
MutablePeriod p1 = new MutablePeriod();
MutablePeriod p2 = new MutablePeriod();
parser.parseInto(p1, s1, 0, Locale.getDefault());
parser.parseInto(p2, s2, 0, Locale.getDefault());
p1.add(p2);
System.out.println(formatter.print(p1));
Prints
34:00:00.222
Related
I have start_time and end_Time, so I tried to print those interval_times (time format 24).
How do I do it?
int start = Integer.parseInt("10:24:49");
int end = Integer.parseInt("11:24:49");
for (int i = start; i < end; i++)
{
System.out.println("result i ="+ i);
}
Since Java 8, the java.time package has been the optimal way to do all date/time related things.
It takes some getting used to, e.g. when it comes to timezones, but it's absolutely worth the effort!
Here's the code for your seconds printer:
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.util.Locale;
public static void main(final String[] args) {
// Just so you know it in the future. Not needed in this example.
final DateTimeFormatter dtfDateTime = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss", Locale.US);
final DateTimeFormatter dtfTime = DateTimeFormatter.ofPattern("HH:mm:ss", Locale.US);
final LocalTime ltStart = LocalTime.of(10, 24, 49);
final LocalTime ltEnd = ltStart.plusHours(1);
// If you want to use String parsing to get your instance:
final LocalTime ltStartViaParsing = LocalTime.from(dtfTime.parse("10:24:49"));
LocalTime i = ltStart;
while (i.isBefore(ltEnd)) {
System.out.println("result i = " + dtfTime.format(i));
i = i.plusSeconds(1);
}
}
Output:
result i = 10:24:49
result i = 10:24:50
result i = 10:24:51
...
result i = 11:24:46
result i = 11:24:47
result i = 11:24:48
It looks like you want to run the loop for particular duration of time.
In case you want to run the loop for fixed duration like for 5 minutes, with a 5 second interval, you can do it like this:
try {
// This loop will run for 5 minutes for every 5 second delay
for(int i=0;i<60;i++) {
System.out.println(new Date());
Thread.sleep(5 * 1000);
}
}
catch (InterruptedException e) {
e.printStackTrace();
}
Before using, see comments below.
If you are intending to print every hour between two given times, then you are totally on the wrong path.
Integer.parseInt
It is intended to get a String number and converts it to Java Integer.
Try to use SimpleDateFormat and Date and Calendar
String startTime = "10:24:49";
String endTime = "11:24:49";
DateFormat sdf = new SimpleDateFormat("hh:mm:ss");
Calendar calendar = Calendar.getInstance();
calendar.setTime(sdf.parse(startTime));
int start = calendar.get(Calendar.HOUR_OF_DAY);
calendar.setTime(sdf.parse(endTime));
int end = calendar.get(Calendar.HOUR_OF_DAY);
This may help:
DateTime startTime, endTime;
Period p = new Period(startTime, endTime);
int hours = p.getHours();
int minutes = p.getMinutes();
And also you can use Java.util.Timer to schedule a thread to be executed at a certain time in the future.
I'm trying to generate a time list in Java. I've read this as to how to add two times together. I wrote the code using floats before converting to using times so I know that the general format of the code works. This is the code that I'm having difficulty with:
public class Test2 {
public static void main(String[] args){
String time = "09:00";
String quarterHour = "00:15";
String halfHour = "00:30";
String quarterHour3 = "00:45";
SimpleDateFormat timeFormat = new SimpleDateFormat("HH:mm");
Date times;
Date temp;
long sum;
try {
times = timeFormat.parse(time);
while(times.before(timeFormat.parse("15:15"))){
System.out.println("Timelist: " + time);
if((times.equals(timeFormat.parse("10:15"))) || (times.equals(timeFormat.parse("13:45")))){
temp = timeFormat.parse(halfHour);
sum = times.getTime() + temp.getTime();
time = timeFormat.format(new Date(sum));
times = timeFormat.parse(time);
}
else if(times.equals(timeFormat.parse("11:45"))){
temp = timeFormat.parse(quarterHour3);
sum = times.getTime() + temp.getTime();
time = timeFormat.format(new Date(sum));
times = timeFormat.parse(time);
}
else{
temp = timeFormat.parse(quarterHour);
sum = times.getTime() + temp.getTime();
time = timeFormat.format(new Date(sum));
times = timeFormat.parse(time);
}
}
} catch (ParseException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
The result I get from that is simply 09:00. It goes through the loop once and ends.
I followed it through the debugger and what's happening is that when it adds the quarterHour to times it adds 12:15 and not the 00:15 as it's supposed to.
This seems to have something to do with me using 24 hour time as when I change the:
SimpleDateFormat timeFormat = new SimpleDateFormat("HH:mm");
to:
SimpleDateFormat timeFormat = new SimpleDateFormat("hh:mm");
It works - except that it goes into an eternal loop.
Question: How do I get it to add only 15 minutes to the time while using 24 hour format?
Use a Calendar, or if you're using Java 8 you might use the new java.time classes like
String timeStr = "09:00";
DateFormat timeFormat = new SimpleDateFormat("HH:mm");
try {
LocalDateTime endTime = LocalDateTime.ofInstant(
Instant.ofEpochMilli(timeFormat.parse("15:15").getTime()),
ZoneOffset.ofHours(0));
Instant instant = Instant.ofEpochMilli(timeFormat.parse(timeStr)
.getTime());
LocalDateTime time = LocalDateTime.ofInstant(instant,
ZoneOffset.ofHours(0));
while (time.isBefore(endTime)) {
time = time.plus(15, ChronoUnit.MINUTES);
Instant output = time.atZone(ZoneOffset.ofHours(0)).toInstant();
System.out.println(timeFormat.format(Date.from(output)));
}
} catch (Exception e) {
e.printStackTrace();
}
or, with the Calendar like
String timeStr = "09:00";
DateFormat timeFormat = new SimpleDateFormat("HH:mm");
try {
Calendar cal = Calendar.getInstance();
cal.setTime(timeFormat.parse(timeStr));
Date when = timeFormat.parse("15:15");
while (cal.getTime().before(when)) {
cal.add(Calendar.MINUTE, 15);
System.out.println(timeFormat.format(cal.getTime()));
}
} catch (Exception e) {
e.printStackTrace();
}
Add this line to your code:
timeFormat.setTimeZone(TimeZone.getTimeZone("GMT"));
immediately after you declare timeFormat.
It fixes your problem on my computer.
For someone else who might stumble here, the link refered to in this question gives misleading results
My First Date: 1986-04-08. Current Date: 2013-11-28.
Code:
public long seconds(Date date){
String formattedDate = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss",getResources().getConfiguration().locale).format(Calendar.getInstance().getTime());
String DateStr=String.valueOf(formattedDate);
Date d = null;
try {
d = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss",getResources().getConfiguration().locale).parse(DateStr);
} catch (ParseException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
java.sql.Date dx = new java.sql.Date(d.getTime());
Date d1 = date;
Date d2 = dx;
t4.setText("BirthDate"+date+"\n Current Date:"+dx);
long seconds = (d2.getTime()-d1.getTime())/1000;
return seconds;
}
However when I check the results here: http://www.calculator.net/age-calculator.html?today=04%2F04%2F1986&ageat=11%2F28%2F2013&x=32&y=10 it gives me a slight different result. I am unsure where I am going wrong.
The online service you link to is wrong: it counts the age as whole days and then assumes that each day is exactly 24 hours long. Most of the time that's correct, but in most places in the world there are days with daylight savings time transitions and timezone transitions, meaning there have been days with 23, 25, or some other number of hours. The number you get from your Java code is more precise.
I think you're somehow mixing java.sql.Date and java.util.Date.
I would try simplifying the code. Something like this.
public class Test012 {
public static void main(String[] args) throws Exception {
System.out.println( seconds() );
System.out.println( seconds2() );
System.out.println( days3() );
}
public static long seconds() throws Exception {
java.text.SimpleDateFormat sdf = new java.text.SimpleDateFormat("yyyy-MM-dd");
java.util.Date d1 = sdf.parse("1986-04-08");
java.util.Date d2 = sdf.parse("2013-11-28");
return ( d2.getTime() - d1.getTime() ) / 1000;
}
public static long seconds2() throws Exception {
java.text.SimpleDateFormat sdf = new java.text.SimpleDateFormat("yyyy-MM-dd");
java.util.Date d1 = sdf.parse("1986-04-08");
java.util.Date d2 = new java.util.Date();
return ( d2.getTime() - d1.getTime() ) / 1000;
}
public static long days3() throws Exception {
java.text.SimpleDateFormat sdf = new java.text.SimpleDateFormat("yyyy-MM-dd");
java.util.Date d1 = sdf.parse("2008-01-01");
java.util.Date d2 = sdf.parse("2009-01-01");
return ( d2.getTime() - d1.getTime() ) / 1000 / 60 / 60 / 24;
}
}
I also tried
select datediff(ss, '4/8/1986', '11/28/2013') --- US date format
in SQL Server and it prints the same thing as this java program,
it prints 872294400. So this seems to be the correct value.
Are you sure the dates coming on your input are the right ones
(are equal to those I hardcoded in my test program)?
I would check that too.
Also, are you sure your dates have zero time parts? That's what the link/service you posted assumes.
Try this code:--
public static long secondsBetween(Calendar startDate, Calendar endDate) {
Calendar date = (Calendar) startDate.clone();
long daysBetween = 0;
while (date.before(endDate)) {
date.add(Calendar.DAY_OF_MONTH, 1);
daysBetween++;
}
return daysBetween*24*3600;
}
Hope it helps you.. Enjoy..!
I have a string holding a start time and an end time in this format 8:30AM - 9:30PM I want to be able to strip out the AM - and the PM and convert all the times to 24 hour format so 9:30PM would really be 21:30 and also have both the times stored in 2 different variables, I know how to strip the string into substrings but Im not sure about the conversion, this is what I have so far. the time variable starts out holding 8:30AM - 9:30PM.
String time = strLine.substring(85, 110).trim();
//time is "8:30AM - 9:30PM"
String startTime;
startTime = time.substring(0, 7).trim();
//startTime is "8:30AM"
String endTime;
endTime = time.substring(9).trim();
//endTime "9:30AM"
Working code (considering that you managed to split the Strings):
public class App {
public static void main(String[] args) {
try {
System.out.println(convertTo24HoursFormat("12:00AM")); // 00:00
System.out.println(convertTo24HoursFormat("12:00PM")); // 12:00
System.out.println(convertTo24HoursFormat("11:59PM")); // 23:59
System.out.println(convertTo24HoursFormat("9:30PM")); // 21:30
} catch (ParseException ex) {
Logger.getLogger(App.class.getName()).log(Level.SEVERE, null, ex);
}
}
// Replace with KK:mma if you want 0-11 interval
private static final DateFormat TWELVE_TF = new SimpleDateFormat("hh:mma");
// Replace with kk:mm if you want 1-24 interval
private static final DateFormat TWENTY_FOUR_TF = new SimpleDateFormat("HH:mm");
public static String convertTo24HoursFormat(String twelveHourTime)
throws ParseException {
return TWENTY_FOUR_TF.format(
TWELVE_TF.parse(twelveHourTime));
}
}
Now that I think about it, SimpleDateFormat, H h K k can be confusing.
Cheers.
You need to use: SimpleDateFormat
And can refer this tutorial: Formatting hour using SimpleDateFormat
Example:
//create Date object
Date date = new Date();
//formatting hour in h (1-12 in AM/PM) format like 1, 2..12.
String strDateFormat = "h";
SimpleDateFormat sdf = new SimpleDateFormat(strDateFormat);
System.out.println("hour in h format : " + sdf.format(date));
I wouldn't reinvent the wheel (unless you are doing this as a school project or some such).
Just get a date object out of your time stamp and then you can generate whatever format you want with this: SimpleDateFormat
[edited to address your specific request]
if you absolutely need to work from your own unique strings, then you'll do something like this (I don't know exactly what your strings look like... you're using offsets like 85, which means nothing out of context).
I didn't check this for bugs, but this is approximately what you want...
myStr = timestampString.toLowerCase(); //something like 8:30am
boolean add12 = (myStr.indexOf("pm") != -1)?true:false;
//convert hour to int
int hour = Integer.parseInt(myStr.split(":")[0]);
int minutes = Integer.parseInt( myStr.split(":")[1].replaceAll("\\D+","").replaceAll("^0+","") ); //get the letters out of the minute part and get a number out of that, also, strip out leading zeros
int militaryTime = hour + (add12)? 12:0;
if(!add12 && militaryTime == 12)
militaryTime = 0; //account for 12am
//dont' forget to add the leading zeros back in as you assemble your string
With Joda Time, the code looks like:
DateTimeFormatter formatter12 = DateTimeFormat.forPattern("K:mma");
DateTime begin = formatter12.parseDateTime(beginTime);
DateTime end = formatter12.parseDateTime(endTime);
DateTimeFormatter formatter24 = DateTimeFormat.forPattern("k:mma");
String begin24 = formatter24.print(begin);
String end24 = formatter24.print(end);
I should like to contribute the modern answer
DateTimeFormatter twelveHourFormatter = DateTimeFormatter.ofPattern("h:mma", Locale.ENGLISH);
String time = "8:30AM - 9:30PM";
String[] times = time.split(" - ");
LocalTime start = LocalTime.parse(times[0], twelveHourFormatter);
System.out.println(start.toString());
LocalTime end = LocalTime.parse(times[1], twelveHourFormatter);
System.out.println(end.toString());
This prints:
08:30
21:30
I am using java.time, the modern Java date and time API. The SimpleDateFormat class used in many of the other answers is long outdated and was always troublesome. java.time is so much nicer to work with than the date-time classes from the 1990’s. A LocalTime is a time of day without a date (and without time zone), so suits your need much better than an old-fashioned Date.
Link: Oracle tutorial: Date Time explaining how to use java.time.
24 hour time adds 12 to any time greater than 12pm so that 1pm is 13 and so on until 24 or 12am. Here is the sudo code:
if(hour <= 12)
{
hour = hour + 12;
}
All the below lines will works when
String str="07:05:45PM";
and when you call timeConversion(str) and want to convert to 24 hours format..
public class TimeConversion {
private static final DateFormat TWELVE_TF = new SimpleDateFormat("hh:mm:ssa");
private static final DateFormat TWENTY_FOUR_TF = new SimpleDateFormat("HH:mm:ss");
static String timeConversion(String s) {
String str = null;
try {
str= TWENTY_FOUR_TF.format(
TWELVE_TF.parse(s));
} catch (ParseException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return str;
}
public static void main(String[] args) throws ParseException {
String str="07:05:45PM";
System.out.println(timeConversion(str));
}
}
I have a Timestamp being passed from an external source to my application in the 2011-01-23-12.31.45 format. I need to compare it to the current system timestamp an make sure its less than 2 minutes difference. Any ideas on how to accomplish this?
That's a date, not a timestamp. You can parse it using java.text.SimpleDateFormat, using the yyyy-dd-MM-HH.mm.ss format:
SimpleDateFormat sdf = new SimpleDateFormat("yyy-dd-MM-HH.mm.ss");
Date date = sdf.parse(inputDateString);
long timestamp = date.getTime();
And then compare - a minute has 60 * 1000 millis.
Using joda-time for date-time operations is always preferred - it will:
have a thread-safe implementation of the dataformat - DateTimeFormat (the one above is not thread-safe)
simply do Minutes.minutesBetween(..) to find out the minutes between the two instants, rather than calculating.
Well this can be optimized but this is what I came up with. It needs some work but it should get you started.
public class Test {
private final String serverValue = "2011-01-23-12.31.45"; //Old should fail
private final String serverValueNew = "2011-03-28-14.02.00"; //New
private SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-HH.mm.ss");
public boolean plusMinusTwoMins(String serverValue) {
boolean withinRange = false;
Date now = Calendar.getInstance().getTime();
Date serverDate = now;
try {
serverDate = dateFormat.parse(serverValue);
} catch (ParseException e) {
e.printStackTrace();
}
long millis = Math.abs(now.getTime() - serverDate.getTime());
System.out.println("Millis: " + millis);
//1000ms * 60s * 2m
if (millis <= (1000 * 60 * 2)) {
withinRange = true;
}
return withinRange;
}
public static void main(String[] args) {
Test test = new Test();
boolean value = test.plusMinusTwoMins(test.serverValue);
System.out.println("Value: " + value);
boolean value2 = test.plusMinusTwoMins(test.serverValueNew);
System.out.println("Value2: " + value2);
}
}