#ifndef VECTOR_COMPLEX_TOOL
#define VECTOR_COMPLEX_TOOL

#include "gsl/gsl_complex.h"
#include "gsl/gsl_complex_math.h"
#include "gsl/gsl_vector.h"
#include "gsl/gsl_vector_double.h"
#include "gsl/gls_vector_complex.h"
#include "gsl/gls_vector_complex_double.h"

#include "Header.hh"

class VectorComplexTool {

    public:
        enum Part {
            REAL; /** the symbol for real      part of complex */
            IMAG; /** the symbol for imagenary prat of complex */
        };

    public:
        /** constructor */
        VectorComplexConv() {};

        /** constructor */
        virtual ~VectorComplexConv() {};

        /** transport a vector as the real part to a complex vector.
         *  @retval the pointer to a gsl_vector_complex type vector
         */
        gsl_vector_complex* toGslVectorComplexReal(const Double*         real, const UInt4 n);
        gsl_vector_complex* toGslVectorComplexReal(const vector<Double>& real);
        gsl_vector_complex* toGslVectorComplexReal(const gsl_vector*     real);

        /** transport a vector as the imagenary part to a complex vector.
         *  @retval the pointer to a gsl_vector_complex type vector
         */
        gsl_vector_complex* toGslVectorComplexImag(const Double*         imag, const UInt4 n);
        gsl_vector_complex* toGslVectorComplexImag(const vector<Double>& imag);
        gsl_vector_complex* toGslVectorComplexImag(const gsl_vector*     imag);

        /** transport two vector to a complex vector.
         *  @retval the pointer to a gsl_vector_complex type vector
         */
        gsl_vector_complex* toGslVectorComplex(const Double*         real, const Double*         imag, const UInt4 n);
        gsl_vector_complex* toGslVectorComplex(const vector<Double>& real, const vector<Double>& imag);
        gsl_vector_complex* toGslVectorComplex(const gsl_vector*     real, const gsl_vector*     imag);

        /** type chage of a vector.
         *  @retval the pointer to a gsl_vector_complex type vector
         */
        gsl_vector_complex* toGslVectorComplex(vector< complex<Double> >& v);

        /** transport a vector as the real part to a complex vector.
         *  @retval the pointer to a vector< complex<Double> > type vector
         */
        vector< complex<Double> >* toVectorComplexReal(const Double*         real, const UInt4 real);
        vector< complex<Double> >* toVectorComplexReal(const vector<Double>& real);
        vector< complex<Double> >* toVectorComplexReal(const gsl_vector*     real);

        /** transport a vector as the imagenary part to a complex vector.
         *  @retval the pointer to a vector< complex<Double> > type vector
         */
        vector< complex<Double> >* toVectorComplexImag(const Double*         imag, const UInt4 real);
        vector< complex<Double> >* toVectorComplexImag(const vector<Double>& imag);
        vector< complex<Double> >* toVectorComplexImag(const gsl_vector*     imag);

        /** transport two vector to a complex vector.
         *  @retval the pointer to a vector< complex<Double> > type vector
         */
        vector< complex<Double> >* toVectorComplex(const Double*         real, const Double*         imag, const UInt4 n);
        vector< complex<Double> >* toVectorComplex(const vector<Double>& real, const vector<Double>& imag);
        vector< complex<Double> >* toVectorComplex(const gsl_vector*     real, const gsl_vector*     imag);

        /** type chage of a vector.
         *  @retval the pointer to a vector< complex<Double> > type vector
         */
        vector< complex<Double> >* toVectorComplex(const gsl_vector_complex* v);

}
#endif // VECTOR_GSL_VECTOR_COMPLEX_H
