Time series data that is retrieved and stored from Oracle and HEC-DSS with the Java programming language uses a class call TimeSeriesContainer.  Date/time values (used mainly for irregular-interval data) are stored in the “int times[]” array.  Also the variable “int julianBaseDate” is included in TimeSeriesContainer.  By default, times[] are in minutes from 01Jan1900 (and can be negative), and julianBaseDate is almost always zero.


TimeSeriesContainer

public class TimeSeriesContainer extends DataContainer implements Cloneable, Serializable

{

public int times[] = null;   //  in minutes since Jan. 01, 1900

       public int julianBaseDate = 0;
JAVA

This convention allowed dates in the range of

Year  -2,182 to year 5,982

Based on a 32-bit integer larges value of 2,147,483,647 before overflowing (and causing garbage.)  In the past, we rarely used dates before 1800 or after 3100, with the year 3000+ used for statistical data.  Character dates (09Jun2017) required a 4 character year (2017).

Recently, changes were made to the Java dev code and DSS-7 code to support dates and times outside of this range.  DSS-7 supports second granularity, and SSP needed large date ranges for computing statistical data.  This necessitated a non-zero julianBaseDate when these features were used (as had always been designed / anticipated.)

To accommodate a very large date range, the variable timeGranularitySeconds was added to TimeSeriesContainer to indicate the number of seconds times in the itimes[] array was given in (e.g., 60 means itimes[] are in minutes, and 3600 means itimes[] are in hours.)  By default, this value is 60 (minutes), or zero (which also indicate minutes).

Also, date functions, both in HecTime and heclib, were modified to accommodate non 4-digit years.  These changes allow a date range of

–5,873,711 to 5,879,610 (01Jan-587371 to 01Jan5879610)

And the software has been tested with this range; however, not all Java dev code has been updated to accommodate this.  Since julianBaseDate was almost always zero, it was generally ignored by programmers.  The correct setting of HecTime from a TimeSeriesContainer is

hecTime.set(tsc.times[i], tsc.timeGranularitySeconds, tsc.julianBaseDate);

This use will be necessary for programs to handle extended dates.

If nothing is done, software should still be able to handle the year range in previous libraries, which is

Year 1000 to year 5000 (01Jan1000 to 01Jan5000)

However, we are encouraging programmers to update software to accommodate extended dates so that software can be used by SSP and other programs that want to take advantage of this capability.

The documentation and an example follows.


Time Series Data with Extended Date Range

DSS-7, and the underlining libraries allow, the use of large dates, often used in statistical analyses.  It has been tested for years from –5,873,711 to 5,879,610, i.e., 01Jan-5873711 to 01Jan5879610 (that’s over 11 million years).  These numbers are based on the largest number that an “int” can hold before overflowing.  DSS-6 had a limit of from year 1,000 to year 4,800 based on int size.

To accommodate these dates, the member timeGranularitySeconds in TimeSeriesContainer specifies what values in the TimeSeriesContainer times array represent.  For regular size data sets, timeGranularitySeconds will match the stored time granularity (although not guaranteed).  For large (time-span) datasets that contain multiple records, timeGranularitySeconds may be returned as 3600 (one hour) or even 86400 (one day).  This means that the times in the times array represent hours or days, not the default of minutes, so that those times do not overflow ints. (This is not to be confused with the time granularity in HecTime, nor the time granularity of how the data is stored in DSS (only minutes or seconds)).  This, along with the Julian base date, allow large ranges of dates for time series data.

To use, set the julianBaseDate in TimeSeriesContainer to the Julian date of the first value, then set timeGranularitySeconds to an accommodating value, such as 3600 for hourly times, and the time array using that granularity.  HecTime objects are set using the following method:

hecTime.set(tsc.times[i], tsc.timeGranularitySeconds, tsc.julianBaseDate);

HecTime objects can also be set using the extended year, such as:

            hecTime.setDate(“01Jan5000000”)

hecTime.setDate(“01Jan-2000”)

When using years less than 1000, keep the year to at least 4 digits with leading zeros (if needed).  For example, the year 20 may have a date of “01Jan0020”, and the year -5 would be “01Jan-005”.   All dates are based on a day count and do not include the 1500 era changes to the calendar, or other similar changes.

When using extended datasets, be careful not to exceed memory.  There are no established limits for DSS, but programs have a finite amount of memory.

An example of storing and reading an extended dateset follows.




Irregular-interval time series data over 50,000 years



import javax.swing.UIManager;

import hec.dataTable.HecDataTableFrame;

import hec.heclib.dss.*;

import hec.heclib.util.HecTime;

import hec.io.TimeSeriesContainer;




//  A simple snippet of code to demonstrate storing and retrieving

//  dataset with very large time spans

//  Be carefull not to exceed memory space!

public class ExampleTimeSeries9 {




        public static void main (String args[])  {




                try {

                javax.swing.UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

                }

                catch (Exception ignore) {}

               

                int numberValues = 2000000;

                //  Write a irregular interval data set.  Gen up the data and times

                //  We are going to be storing data from the year 1,000 to 55,758

                //  and store one value every 10 days for 2,000,000 values

                TimeSeriesContainer tsc = new TimeSeriesContainer();

                HecTime hecTime = new HecTime("20Jan1000", "1200");

                tsc.julianBaseDate = hecTime.julian();

                tsc.timeGranularitySeconds = 86400;

                tsc.values = new double[numberValues];

                //  Irregular interval data requires the times array

                tsc.times = new int[numberValues];

                tsc.numberValues = numberValues;

                for (int i=0; i<numberValues; i++) {

                        tsc.values[i] = (double)i;

                        tsc.times[i] = i * 10;  //  one value every 10 days               

                }              

               

                tsc.fullName = "/Basin/Location/Flow//Ir-Century/Extended dates/";

                tsc.units = "CFS";

                tsc.type = "Inst-Val"; 

                HecTimeSeries dssTimeSeries = new HecTimeSeries();

                dssTimeSeries.setDSSFileName("C:/temp/Test7.dss");      

                int status = dssTimeSeries.write(tsc);

                dssTimeSeries.done();          

                if (status != 0) return;

               

                //  Read data

                TimeSeriesContainer tscRead = new TimeSeriesContainer();        

                tscRead.fullName = "/Basin/Location/Flow//Ir-Century/Extended dates/";               

                tscRead.retrieveAllTimes = true;

                HecTimeSeries dssTimeSeriesRead = new HecTimeSeries();

                dssTimeSeriesRead.setDSSFileName("C:/temp/Test7.dss");          

                status = dssTimeSeriesRead.read(tscRead, true);

                dssTimeSeriesRead.done();               

                if (status != 0) return;




                //  Show in a table

                HecDataTableFrame tableFrame = new HecDataTableFrame(null);

                tableFrame.setData(tscRead);

                tableFrame.setVisible(true);

       

                //  If an HecTime object was to be set for this dataset, it would use this call

                //  hecTime.set(tscRead.times[i], tscRead.timeGranularitySeconds, tscRead.julianBaseDate);




                HecDataManager.closeAllFiles();

        }
JAVA