elementary_functions module.
[scilab.git] / scilab / modules / elementary_functions / sci_gateway / cpp / sci_exp.cpp
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2012 - DIGITEO - Cedric DELAMARRE
4  *
5  * This file must be used under the terms of the CeCILL.
6  * This source file is licensed as described in the file COPYING, which
7  * you should have received as part of this distribution.  The terms
8  * are also available at
9  * http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
10  *
11  */
12 /*--------------------------------------------------------------------------*/
13 #include "elem_func_gw.hxx"
14 #include "function.hxx"
15 #include "double.hxx"
16 #include "overload.hxx"
17 #include "execvisitor.hxx"
18
19
20 extern "C"
21 {
22 #include "Scierror.h"
23 #include "localization.h"
24 #include "exp.h"
25 }
26
27 /*--------------------------------------------------------------------------*/
28 types::Function::ReturnValue sci_exp(types::typed_list &in, int _iRetCount, types::typed_list &out)
29 {
30     if (in.size() != 1)
31     {
32         ScierrorW(77, _W("%ls: Wrong number of input argument(s): %d to %d expected.\n"), L"exp", 1);
33         return types::Function::Error;
34     }
35
36     if (_iRetCount > 1)
37     {
38         ScierrorW(78, _W("%ls: Wrong number of output argument(s): %d expected.\n"), L"exp", 1);
39         return types::Function::Error;
40     }
41
42     if (in[0]->isDouble())
43     {
44         types::Double* pDblIn = in[0]->getAs<types::Double>();
45         types::Double* pDblOut = new types::Double(pDblIn->getDims(), pDblIn->getDimsArray(), pDblIn->isComplex());
46
47         if (pDblIn->isComplex())
48         {
49             for (int i = 0; i < pDblIn->getSize(); i++)
50             {
51                 zexps(pDblIn->get(i), pDblIn->getImg(i), pDblOut->get() + i, pDblOut->getImg() + i);
52             }
53         }
54         else
55         {
56             for (int i = 0; i < pDblIn->getSize(); i++)
57             {
58                 pDblOut->set(i, dexps(pDblIn->get(i)));
59             }
60         }
61
62         out.push_back(pDblOut);
63     }
64     else if (in[0]->isSparse())
65     {
66         types::Sparse* pSparseIn = in[0]->getAs<types::Sparse>();
67         types::Sparse* pSparseOut = new types::Sparse(pSparseIn->getRows(), pSparseIn->getCols(), pSparseIn->isComplex());
68
69         int const nonZeros = static_cast<int>(pSparseIn->nonZeros());
70         double* pRows = new double[nonZeros * 2];
71         pSparseIn->outputRowCol(pRows);
72         double* pCols = pRows + nonZeros;
73
74         double* pNonZeroR = new double[nonZeros];
75         double* pNonZeroI = new double[nonZeros];
76         pSparseIn->outputValues(pNonZeroR, pNonZeroI);
77
78         if (pSparseIn->isComplex())
79         {
80             for (int i = 0; i < nonZeros; i++)
81             {
82                 std::complex<double> complex;
83                 double dblReal = complex.real();
84                 double dblImg = complex.imag();
85                 zexps(pNonZeroR[i], pNonZeroI[i], &dblReal, &dblImg);
86                 pSparseOut->set(pRows[i] - 1, pCols[i] - 1, complex);
87             }
88         }
89         else
90         {
91             for (int i = 0; i < nonZeros; i++)
92             {
93                 pSparseOut->set(pRows[i] - 1, pCols[i] - 1, dexps(pNonZeroR[i]));
94             }
95         }
96
97         delete[] pRows;
98         delete[] pNonZeroR;
99         delete[] pNonZeroI;
100
101         out.push_back(pSparseOut);
102     }
103     else
104     {
105         std::wstring wstFuncName = L"%"  + in[0]->getShortTypeStr() + L"_exp";
106         return Overload::call(wstFuncName, in, _iRetCount, out, new ExecVisitor());
107     }
108
109     return types::Function::OK;
110 }
111 /*--------------------------------------------------------------------------*/