/***************************************************************************
**
**  This file is part of GeopsyCore.
**
**  GeopsyCore is free software: you can redistribute it and/or modify
**  it under the terms of the GNU General Public License as published by
**  the Free Software Foundation, either version 3 of the License, or
**  (at your option) any later version.
**
**  GeopsyCore is distributed in the hope that it will be useful,
**  but WITHOUT ANY WARRANTY; without even the implied warranty of
**  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
**  GNU General Public License for more details.
**
**  You should have received a copy of the GNU General Public License
**  along with Foobar.  If not, see <http://www.gnu.org/licenses/>
**
**  See http://www.geopsy.org for more information.
**
**  Created: 2003-11-22
**  Copyright: 2003-2019
**    Marc Wathelet
**    Marc Wathelet (ULg, Liège, Belgium)
**    Marc Wathelet (LGIT, Grenoble, France)
**
***************************************************************************/

#include "SignalTemplate.h"

namespace GeopsyCore {

/*!
  \class SignalTemplate SignalTemplate.h
  \brief Template class to store signals

  Samples can be any number with arithmetic operators (int, float, double, or Complex). For double and complex
  numbers, the most appropriate object might be DoubleSignal and ComplexSignal, respectively.

  All operations on signals assume that the signal is not locked. You can lock signal before but it is useless.
*/

/*!
  \fn SignalTemplate<sampleType>::SignalTemplate( )
  Set the number of samples as 0. Before allocating signals (first call to LOCK_SAMPLES), be sure to set the correct
  number of samples with setNSamples().
*/

/*!
  \fn SignalTemplate<sampleType>::SignalTemplate(int n)
  Set the number of samples as \a n.
*/

/*!
  \fn SignalTemplate<sampleType>::SignalTemplate(const SignalTemplate<sampleType>& o)
  Set the same number of samples as \a o. No sample values are copied.
*/

/*!
  \fn virtual SignalTemplate<sampleType>::~SignalTemplate()
  Frees internal sample vector.
*/

/*!
  \fn bool SignalTemplate<sampleType>::LOCK_SAMPLES
  General function to be called before using the sample vector returned by samples().
*/

/*!
  \fn inline void SignalTemplate<sampleType>::freeSamples()
  Frees the internal sample vector. This cannot be called between LOCK_SAMPLES and UNLOCK_SAMPLES.
*/

/*!
  \fn int SignalTemplate<sampleType>::nSamples() const
  Returns the number of samples.
*/

/*!
  \fn void SignalTemplate<sampleType>::setNSamples(int n)
  Set \a n as the number of samples. The signal cannot be allocated when calling this function.
  isAllocated() tells whether the samples are allocated. Samples are allocated after a first call to LOCK_SAMPLES.
  UNLOCK_SAMPLES does not necessarely deallocates the samples. To effectively deallocate the samples call freeSamples().
*/

/*!
  \fn sampleType * SignalTemplate<sampleType>::samples() const
  Returns a vector with the samples. its length is given by nSamples(). This vector must be used ONLY between
  LOCK_SAMPLES and UNLOCK_SAMPLES. Outside, there is not guaranties that the pointer points to the samples, especially
  in multi thred context.
*/

/*!
  \fn void SignalTemplate<sampleType>::multiply(SignalTemplate<sampleType> * sig)
  Multiplies signal \a sig samples to the samples of this signals (sample by sample). If the number of samples
  is not the same for both signals, nothing is done.
*/

/*!
  \fn void SignalTemplate<sampleType>::multiply(sampleType value)
  Multiplies all samples by \a value.
*/

/*!
  \fn void SignalTemplate<sampleType>::subtract(SignalTemplate<sampleType> * sig)
  Subtracts all samples of this signal by the \a sig samples (sample by sample). If the number of samples
  is not the same for both signals, only the common part if affected.
*/

/*!
  \fn void SignalTemplate<sampleType>::range(sampleType& min, sampleType& max)
  Returns the \a min and \a max of the sample values.
*/

/*!
  \fn sampleType SignalTemplate<sampleType>::maximum()
  Returns the maximum of the sample values.
*/

/*!
  \fn sampleType SignalTemplate<sampleType>::average(int startAt, int nSamples)
  Returns the average of the sample values starting at \a startAt and for only \a nSamples.
*/

/*!
  \fn sampleType SignalTemplate<sampleType>::average2(int startAt, int nSamples)
  Returns the average of the squared sample values starting at \a startAt and for only \a nSamples.
  Note that the squared sum is divided by (nSamples -1). To compute the standard deviation, combine
  this result with average():

  \begincode
  int n=s->nSamples();
  stddev=s->average2(0,n) - n/(n-1)*s->average(0,n);
  \endcode
*/

/*!
  \fn int SignalTemplate<sampleType>::add(SignalTemplate<sampleType> * sig, int sigStart=0, int thisStart=0, int nToCopy=-1, bool checkInvalid=false, sampleType invalidValue=0);
  Add \a nToCopy samples of this signal with the \a sig samples (sample by sample) starting at \a sigStart index
  from beginning of \a sig. Samples are copied to this signal starting at index \a thisStart. if \a checkInvalid
  is true sample values are check for invalid value \a invalidValue. All matching samples are discarded from the sum.

  The number of summed samples is returned. It is equal to \a nToCopy is no invalid value is found and if signals
  sufficiently overlap (from indexes \a sigStart and \a thisStart).
*/

/*!
  \fn void SignalTemplate<sampleType>::initValues(sampleType value, int startAt, int nSamples)
  Set sample values to \a value, starting at \a startAt and for \a nSamples only.
*/

/*!
  \fn int SignalTemplate<sampleType>::findValue(sampleType value, int from, bool whileNotFound=false)
  Scans signal starting at \a from for value \a value. If \a whileNotFound is true, scan is runs until finding
  \a value. On the contrary, if it is false, the scan stops if the signal samples differ from \a value.
  In both cases, if the end of the signal is reached, the total number of samples is returned.
*/

/*!
  \fn void SignalTemplate<sampleType>::debugPrint()
  Prints all sample values to stdout. This function is usually reserved for debug.
*/

/*!
  \fn void SignalTemplate<sampleType>::adjustLimits(SignalTemplate<sampleType> * sig, int& sigStart, int& thisStart, int& nToCopy) const;
  Internal function to adjust \a sigStart, \a thisStart and \a nToCopy to fit only the common part of these
  two signal.
*/

/*!
  \fn SignalTemplate<sampleType>::bool isAllocated() const
  Returns true is samples are allocated. Used by Cache.
*/

/*!
  \fn int SignalTemplate<sampleType>::dataSize() const
  Returns the memory space in bytes used by the internal sample vector. Used by Cache.
*/

/*!
  \fn double SignalTemplate<sampleType>::dataSizeMb() const
  Returns the memory space in Nbytes used by the internal sample vector. Used by Cache.
*/

/*!
  \fn bool SignalTemplate<sampleType>::allocate()
  Allocate the sample vector. Used by Cache.
*/

/*!
  \fn void SignalTemplate<sampleType>::free()
  Deallocate the sample vector. Used by Cache.
*/

/*!
  \fn void SignalTemplate<sampleType>::save(QDir& d)
  Save samples to directory \a d using a raw binary format. Used by Cache.
  \a d is normarly a temporary directory.

  \sa load()
*/

/*!
  \fn void SignalTemplate<sampleType>::load(QDir& d)
  Loads samples from directory \a d using a raw binary format. Used by Cache.
  \a d is normarly a temporary directory.

  \sa save()
*/

/*!
  \fn void SignalTemplate<sampleType>::copySamplesFrom(SignalTemplate<sampleType> * sig);
  Copies all samples from signal \a sig start to this signal. If the number of samples is not the same for both
  signals, nothing is done.
*/

/*!
  \fn bool SignalTemplate<sampleType>::copySamplesFrom(SignalTemplate<sampleType> * sig, int sigStart, int thisStart, int nToCopy);
  Copies \a nToCopy samples from signal \a sig starting at \a sigStart index from beginning of \a sig. Samples
  are copied to this signal starting at index \a thisStart.
*/

} // namespace GeopsyCore
