예제 #1
0
 public void FillDateArray(
     TSDateCalculator.TimeStepUnitCode timeStepUnit, short timeStepQuantity,
     int nReqValues, DateTime[] dateArray, DateTime reqStartDate)
 {
     TSDateCalculator.FillDateArray(timeStepUnit, timeStepQuantity,
                                    nReqValues, dateArray, reqStartDate);
 }
예제 #2
0
        /// <summary>
        /// Method fills in the values of the given array of DateTime values with the dates for
        /// each time step in the time series that matches the given ID.  The array is filled
        /// starting at the given start date, or the start date of the database record, whichever
        /// is earliest.  The array is filled up the the given number of values.
        /// </summary>
        /// <param name="id">ID of the time series</param>
        /// <param name="nReqValues">number of values requested to be filled</param>
        /// <param name="dateArray">array requested to fill with values</param>
        /// <param name="reqStartDate">start date requested</param>
        public unsafe void FillDateArray(int id,
                                         int nReqValues, DateTime[] dateArray, DateTime reqStartDate)
        {
            // Initialize class fields
            if (!IsInitialized)
            {
                Initialize(id);
            }

            int      i;
            DateTime revisedStartDate;

            // The time steps boundaries are defined by the database record, so
            // we can't rely on the reqStartDate to have the correct time step boundary.
            // Therefore, begin counting at the first date in the database record.
            if (reqStartDate > BlobStartDate)
            {
                i = TSDateCalculator.CountSteps(BlobStartDate, reqStartDate, TimeStepUnit, TimeStepQuantity);
                revisedStartDate = TSDateCalculator.IncrementDate(BlobStartDate, TimeStepUnit, TimeStepQuantity, i);
            }
            else
            {
                revisedStartDate = BlobStartDate;
            }

            TSDateCalculator.FillDateArray(TimeStepUnit, TimeStepQuantity,
                                           nReqValues, dateArray, revisedStartDate);
        }
예제 #3
0
        /// <summary>
        /// This method prepares a new record for the trace table for a regular time step series.
        /// The method converts the given valueArray into the BLOB that is actually stored in
        /// the table.  The method computes the checksum of the trace, and computes a new checksum
        /// for the parameters table to reflect the fact that a new trace has been added to the ensemble.
        /// For both the insertion to the trace table and the update to the parameters table, this method
        /// only stores changes in DataTable objects--nothing is changed in the database. In order for
        /// the changes to be sent to the database, the method TSConnection.CommitNewTraceWrites must
        /// be called after WriteTraceRegular has been called for all new traces.
        /// </summary>
        /// <param name="id">identifying primary key value of the the parameters table for the record
        /// that this trace belongs to</param>
        /// <param name="doWriteToDB">true if the method should actually save the timeseries to the database</param>
        /// <param name="tsImport">TSImport object into which the method will record values that it has computed.
        /// If this parameter is null, then the method will skip the recording of such paramters to an object.</param>
        /// <param name="traceNumber">number of the trace to write</param>
        /// <param name="valueArray">The array of values to be written to the database</param>
        public unsafe void WriteTraceRegular(int id,
                                             bool doWriteToDB, TSImport tsImport,
                                             int traceNumber,
                                             double[] valueArray)
        {
            // Initialize class fields other than the BLOB of data values
            if (!IsInitialized)
            {
                Initialize(id, true);
            }

            // This method can only process regular-time-step series
            if (TimeStepUnit == TSDateCalculator.TimeStepUnitCode.Irregular)
            {
                throw new TSLibraryException(ErrCode.Enum.Record_Not_Regular,
                                             String.Format("The method can only process regular time series, but" +
                                                           "the record with Id {0} is irregular.", id));
            }
            // Create a trace object
            int timeStepCount            = valueArray.Count();
            ITimeSeriesTrace traceObject = new TSTrace
            {
                TraceNumber   = traceNumber,
                TimeStepCount = timeStepCount,
                EndDate       = TSDateCalculator.IncrementDate(BlobStartDate,
                                                               TimeStepUnit, TimeStepQuantity, timeStepCount - 1)
            };

            if (tsImport != null)
            {
                tsImport.TraceList.Add(traceObject);
            }
            else
            {
                TraceList.Add(traceObject);
            }
            // Convert the array of double values into a byte array...a BLOB
            TSBlobCoder.ConvertArrayToBlobRegular(valueArray, CompressionCode, traceObject);

            // Create a new record for the trace table
            // (but for now it is only stored in a DataTable object)
            if (doWriteToDB)
            {
                WriteTrace(traceObject);
            }
            // Compute a new checksum for the parameters table
            // (but for now it is only stored in a DataTable object)
            UpdateParametersChecksum(doWriteToDB, tsImport);
        }
예제 #4
0
 public int CountTimeSteps(DateTime startDate, DateTime endDate,
                           short unit, short stepSize)
 {
     return(TSDateCalculator.CountSteps(startDate, endDate, (TSDateCalculator.TimeStepUnitCode)unit, stepSize));
 }
예제 #5
0
 public DateTime IncrementDate(DateTime startDate, TSDateCalculator.TimeStepUnitCode unit,
                               short stepSize, int numSteps)
 {
     return(TSDateCalculator.IncrementDate(startDate, unit, stepSize, numSteps));
 }
예제 #6
0
        /// <summary>
        /// This private method creates a List of TimeSeriesValue objects from the given BLOB (byte array)
        /// of time series values.  The method takes parameters for a maximum number of values,
        /// an earliest date, and a latest date, so that only a portion of the BLOB might be
        /// converted to the List.  This method is designed to do the operations that are common between
        /// the public methods ConvertBlobToListLimited() and ConvertBlobToListAll().
        /// </summary>
        /// <param name="timeStepUnit">TSDateCalculator.TimeStepUnitCode value for Minute,Hour,Day,Week,Month, Year, or Irregular</param>
        /// <param name="timeStepQuantity">The number of the given unit that defines the time step.
        /// For instance, if the time step is 6 hours long, then this value is 6.  If timeStepUnit is
        /// Irregular, then this value is ignored.</param>
        /// <param name="timeStepCount">the number of time steps that are stored in the blob</param>
        /// <param name="blobStartDate">The DateTime value of the first time step in the BLOB. If
        /// timeStepUnit is Irregular, then this value is ignored.</param>
        /// <param name="applyLimits">If value is true, then nReqValues, reqStartDate, and reqEndDate will be
        /// used to limit the portion of the BLOB that is converted to dateValueList.  If the value is false, then
        /// nReqValues, reqStartDate, and reqEndDate will be ignored.</param>
        /// <param name="nReqValues">The maximum number of time steps that should be added to dateValueList.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="reqStartDate">The earliest date that will be added to dateValueList.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="reqEndDate">The latest date that will be added to dateValueList.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="blobData">The BLOB (byte array) that this method will convert into a List</param>
        /// <param name="dateValueList">The List of TimeSeriesValues that this method will create from the BLOB.</param>
        /// <param name="compressionCode">a generation number that indicates what compression technique to use</param>
        /// <returns>The number of time steps added to dateValueList</returns>
        private unsafe int ConvertBlobToList(
            TSDateCalculator.TimeStepUnitCode timeStepUnit, short timeStepQuantity,
            int timeStepCount, DateTime blobStartDate, Boolean applyLimits,
            int nReqValues, DateTime reqStartDate, DateTime reqEndDate,
            Byte[] blobData, ref List <TimeSeriesValue> dateValueList, int compressionCode)
        {
            int nValuesRead = 0;

            if (timeStepUnit == TSDateCalculator.TimeStepUnitCode.Irregular)
            {
                // IRREGULAR TIME SERIES

                // If we're not limiting the output list (i.e., we're returning every time step from
                // the BLOB), then set the size of the intermediate array to match the size of the BLOB.
                if (applyLimits == false)
                {
                    nReqValues = timeStepCount;
                }
                // Allocate an array of date/value pairs that TSBlobCoder method will fill
                TSDateValueStruct[] dateValueArray = new TSDateValueStruct[nReqValues];
                // Method in the TSBlobCoder class does the real work
                nValuesRead = TSBlobCoder.ConvertBlobToArrayIrregular(timeStepCount, applyLimits,
                                                                      nReqValues, reqStartDate, reqEndDate,
                                                                      blobData, dateValueArray, compressionCode);
                // resize the array so that the List that we make from it will have exactly the right size
                if (nValuesRead != nReqValues)
                {
                    Array.Resize <TSDateValueStruct>(ref dateValueArray, nValuesRead);
                }
                // Convert the array of date/value pairs into the List that will be used by the caller
                dateValueList = dateValueArray
                                .Select(tsv => (TimeSeriesValue)tsv).ToList <TimeSeriesValue>();
            }
            else
            {
                // REGULAR TIME SERIES

                // If we're not limiting the output list (i.e., we're returning every time step from
                // the BLOB), then set the size of the intermediate array to match the size of the BLOB.
                if (applyLimits == false)
                {
                    nReqValues = timeStepCount;
                }
                // Allocate an array of values that TSBlobCoder method will fill
                double[] valueArray = new double[nReqValues];
                // Method in the TSBlobCoder class does the real work
                nValuesRead = TSBlobCoder.ConvertBlobToArrayRegular(timeStepUnit, timeStepQuantity,
                                                                    timeStepCount, blobStartDate, applyLimits,
                                                                    nReqValues, reqStartDate, reqEndDate,
                                                                    blobData, valueArray, compressionCode);
                // Allocate an array to hold the time series' date values
                DateTime[] dateArray = new DateTime[nValuesRead];
                // Fill the array with the date values corresponding to the time steps defined
                // for this time series in the database.
                TSDateCalculator.FillDateArray(timeStepUnit, timeStepQuantity, nValuesRead, dateArray, reqStartDate);
                // Allocate a List of date/value pairs that will be used by the caller
                dateValueList = new List <TimeSeriesValue>(nValuesRead);
                // Loop through all values, building the List of date/value pairs out of the
                // primitive array of dates and primitive array of values.
                int i;
                for (i = 0; i < nValuesRead; i++)
                {
                    dateValueList.Add(new TimeSeriesValue {
                        Date = dateArray[i], Value = valueArray[i]
                    });
                }
                nValuesRead = i;
            }
            return(nValuesRead);
        }
예제 #7
0
        /// <summary>
        /// This method converts a BLOB (byte array) to an array of regular time step timeseries
        /// values (double precision floats).  The caller must give parameters of the
        /// time series, such as time step size and start date.  The method will convert
        /// only a portion of the BLOB if the applyLimits parameter is true, according to
        /// the parameter values nReqValues, reqStartDate, and reqEndDate.  If the
        /// applyLimits parameter is false, then the method converts the entire BLOB into
        /// the given array of values.  The array of values must have been allocated
        /// large enough prior to calling this method.
        /// </summary>
        /// <param name="timeStepUnit">TSDateCalculator.TimeStepUnitCode value for Minute,Hour,Day,Week,Month, Year, or Irregular</param>
        /// <param name="timeStepQuantity">The number of the given unit that defines the time step.
        /// For instance, if the time step is 6 hours long, then this value is 6.</param>
        /// <param name="timeStepCount">the number of time steps that are stored in the blob</param>
        /// <param name="blobStartDate">Date of the first time step in the BLOB</param>
        /// <param name="applyLimits">If true, then the method will convert only a portion of the BLOB,
        /// according to the parameter values nReqValues, reqStartDate, and reqEndDate.  If false, the method
        /// converts the entire BLOB into a value array.</param>
        /// <param name="nReqValues">The maximum number of elements that will be converted into the array of values.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="reqStartDate">The earliest date in the time series that will be written to the array of values.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="reqEndDate">The latest date in the time series that will be written to the array of values.
        /// If applyLimits==false, then this value is ignored.</param>
        /// <param name="blobData">the BLOB that will be converted</param>
        /// <param name="valueArray">the array of time series values that is produced from the BLOB</param>
        /// <param name="compressionCode">a generation number that indicates what compression technique to use</param>
        /// <returns>The number of time steps that were actually written to valueArray</returns>
        public static unsafe int ConvertBlobToArrayRegular(
            TSDateCalculator.TimeStepUnitCode timeStepUnit, short timeStepQuantity,
            int timeStepCount, DateTime blobStartDate, bool applyLimits,
            int nReqValues, DateTime reqStartDate, DateTime reqEndDate,
            Byte[] blobData, double[] valueArray, int compressionCode)
        {
            // The BLOB is kept in a compressed form, so our first step is to decompress it before
            // anything else can be done.
            Byte[] decompressedBlobData
                = DecompressBlob(blobData, timeStepCount * sizeof(double), compressionCode);

            // MemoryStream and BinaryReader objects enable bulk copying of data from the BLOB
            using (MemoryStream blobStream = new MemoryStream(decompressedBlobData))
                using (BinaryReader blobReader = new BinaryReader(blobStream))
                {
                    // How many elements of size 'double' are in the BLOB?
                    int numBlobBin    = (int)blobStream.Length;
                    int numBlobValues = numBlobBin / sizeof(double);

                    int numReadValues  = numBlobValues;
                    int numSkipValues  = 0;
                    int numTruncValues = 0;

                    // Values might be skipped from the front or truncated from the end of the array,
                    // but only if this flag is 'true'.
                    if (applyLimits)
                    {
                        // Do we skip any values at the front of the BLOB in order to fullfil the requested start date?
                        if (reqStartDate > blobStartDate)
                        {
                            numSkipValues = TSDateCalculator.CountSteps(blobStartDate, reqStartDate,
                                                                        timeStepUnit, timeStepQuantity);
                        }
                        // compute the last date in the BLOB
                        DateTime blobEndDate = TSDateCalculator.IncrementDate
                                                   (blobStartDate, timeStepUnit, timeStepQuantity, numBlobValues - 1);
                        // Do we truncate any values at the end of the BLOB in order to fulfill the requested end date?
                        if (reqEndDate < blobEndDate)
                        {
                            numTruncValues = TSDateCalculator.CountSteps(reqEndDate, blobEndDate,
                                                                         timeStepUnit, timeStepQuantity);
                        }
                        // the number of values that can actually be read from the BLOB
                        numReadValues = Math.Min(numBlobValues - numSkipValues - numTruncValues, nReqValues);
                    }

                    // the number of bytes that will actually be read
                    int numReadBin = numReadValues * sizeof(double);
                    // the number of bytes that will be skipped
                    int numSkipBin = numSkipValues * sizeof(double);

                    // If we've got zero values to read, then we're done early!
                    if (numReadValues <= 0)
                    {
                        return(0);
                    }

                    // Transfer the entire array of data as a block
                    Buffer.BlockCopy(blobReader.ReadBytes(numBlobBin), numSkipBin, valueArray, 0, numReadBin);

                    return(numReadValues);
                }
        }