I am developing a race timing system, and for several instances, I need to retrieve a time object from H2DB. Like its bretheren (or sisteren), the time data type is relative to 1st January 1970 and is expressed in SQL in the 'hh:mm:ss' format, with the date being by set by default to 01-01-1970. It is by default mapped to the a 'java.sql.Time' object. Being a trusting padawan, I coded the following to separate hours from minutes for display purposes.
if(race.getCutOffTime()!=null){
long cutOffHour=(race.getCutOffTime().getTime())/(3600000);
int cutOffMinute=(int)(race.getCutOffTime().getTime()%(60*60*1000));
System.out.println(cutOffHour+":"+cutOffMinute);
}
Java's time handling stink arises however in that these functions output unexpected values, for example, the following statement from my db, gives an output of 3:30.
INSERT INTO MagEye.Races(RaceName, EventID,CutOffTime)
VALUES ('TEST', SELECT EventID FROM MagEye.Events
WHERE EventName='Sabrina Love',TIME '5:50:00');
Changing this statement to reflect a time of '0:0:0', gives me a value of "-2:00" What am I doing wrong? Thank you (in advance).
Edit As requested, here is my code for the database:
Table Creation Statement:
CREATE TABLE IF NOT EXISTS MagEye.Races (RaceID INT PRIMARY KEY AUTO_INCREMENT , RaceName VARCHAR(100) ,EventID INT, Description TEXT, MaxEntrants INT, MinAge INT, MaxAge INT, RacePrefix VARCHAR (5), TimingMethod CHAR(1), CutOffTime TIME, RaceEnd TIMESTAMP,Finished BOOLEAN DEFAULT FALSE, Autostart BOOLEAN, FOREIGN KEY(EventID) REFERENCES MagEye.Events(EventID));
Insertion Statement:
INSERT INTO MagEye.Races(RaceName, EventID,CutOffTime) VALUES ('TEST', SELECT EventID FROM MagEye.Events WHERE EventName='Sabrina Love',TIME '5:50:00');
Retrieval:
raceDB.result = raceDB.state.executeQuery("SELECT * FROM MagEye.Races WHERE EventID=" + eventID + " ORDER BY RaceName");
java.util.ArrayList<Race> races = new java.util.ArrayList<>();
while (raceDB.result.next()) {
Race thisRace;
String timingMethodString = raceDB.result.getString("TimingMethod");
Race.TimingMethod timingMethod = null;
if (timingMethodString != null) {
timingMethod = Race.TimingMethod.valueOf(timingMethodString);
} else {
timingMethod = Race.TimingMethod.MANUAL;
}
thisRace = new Race(raceDB.result.getInt("RaceID"), event, raceDB.result.getString("RaceName"), raceDB.result.getString("Description"), raceDB.result.getInt("MaxEntrants"), raceDB.result.getInt("MinAge"), raceDB.result.getInt("MaxAge"), raceDB.result.getString("RacePrefix"), timingMethod,(raceDB.result.getTime("CutOffTime")), raceDB.result.getBoolean("Autostart"));
thisRace = new Race(raceDB.result.getInt("RaceID"), event, raceDB.result.getString("RaceName"), raceDB.result.getString("Description"), raceDB.result.getInt("MaxEntrants"), raceDB.result.getInt("MinAge"), raceDB.result.getInt("MaxAge"), raceDB.result.getString("RacePrefix"), timingMethod,(raceDB.result.getTime("CutOffTime")), raceDB.result.getBoolean("Autostart"));
Display:
if(race.getCutOffTime()!=null){
long cutOffHour=(int)(race.getCutOffTime().getTime())/(3600000);
RacesCutOffLength.setText(cutOffHour+"");
int cutOffMinute=(int)(race.getCutOffTime().getTime()%(60*60*1000));
this.RacesMinutes.setText(cutOffMinute+"");
}
else{
RacesCutOffLength.setText("0");
RacesMinutes.setText("0");
}
Edit : I've decided to replace the Time object with a long primative
java.util.Date
is always the UTC time. So, depending of your locale, there will be probably an offset.
I have heard of Joda Time
as a better Java API for dealing with times.
Anyway, the problem comes from mixing dates treated by java.util.Date
and others directly passed as part of the SQL.
As long as you keep using java.util/sql.Date
for everything (and you don't peak inside the DB)(and you don't change the locale) the results will be coherent. The trouble will begin when your SQL tries to pass the values directly as text. So either use Date
everywhere or, as trashgod says, everytime you use a Date
you take care of setting the Locale to "GMT" (so the internal representation and the output of the Date are the same). Note that this does include Date
returned from the DB
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.