6f5fe0a833ae623a59c62ca47bd487d9bb226edf
[scilab.git] / scilab / modules / string / sci_gateway / cpp / sci_tokens.cpp
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) Digiteo 2011 - Cedric DELAMARRE
4  *
5  * Copyright (C) 2012 - 2016 - Scilab Enterprises
6  *
7  * This file is hereby licensed under the terms of the GNU GPL v2.0,
8  * pursuant to article 5.3.4 of the CeCILL v.2.1.
9  * This file was originally licensed under the terms of the CeCILL v2.1,
10  * and continues to be available under such terms.
11  * For more information, see the COPYING file which you should have received
12  * along with this program.
13  *
14  */
15
16
17 #include "function.hxx"
18 #include "string.hxx"
19 #include "list.hxx"
20 #include "double.hxx"
21 #include "function.hxx"
22 #include "string_gw.hxx"
23
24 extern "C"
25 {
26 #include "sci_malloc.h"
27 #include "os_string.h"
28 #include "tokens.h"
29 #include "core_math.h"
30 #include "localization.h"
31 #include "Scierror.h"
32 }
33
34 #include <sciprint.h>
35
36 types::Function::ReturnValue sci_tokens(types::typed_list &in, int _iRetCount, types::typed_list &out)
37 {
38     types::String* pOutString   = NULL;
39     types::String* pString      = NULL;
40     types::String* pCharSample  = NULL;
41     wchar_t* seps               = NULL;
42     int sizeSeps                = 0;
43
44     if (in.size() > 2 || in.size() == 0)
45     {
46         Scierror(77, _("%s: Wrong number of input argument(s): %d to %d expected.\n"), "tokens", 1, 2);
47         return types::Function::Error;
48     }
49     if (_iRetCount != 1)
50     {
51         Scierror(78, _("%s: Wrong number of output argument(s): %d expected.\n"), "tokens", 1);
52         return types::Function::Error;
53     }
54
55     // first arg
56     if (in[0]->isString() == false)
57     {
58         Scierror(999, _("%s: Wrong type for input argument #%d: String expected.\n"), "tokens", 1);
59         return types::Function::Error;
60     }
61     pString = in[0]->getAs<types::String>();
62     if (pString->isScalar() == false)
63     {
64         Scierror(999, _("%s: Wrong size for input argument #%d.\n"), "tokens", 1);
65         return types::Function::Error;
66     }
67     if (wcslen(pString->get(0)) == 0)
68     {
69         types::Double* pOutDouble = types::Double::Empty();
70         out.push_back(pOutDouble);
71         return types::Function::OK;
72     }
73
74     // second arg
75     if (in.size() == 2)
76     {
77         if (in[1]->isString() == false)
78         {
79             Scierror(999, _("%s: Wrong type for input argument #%d: String expected.\n"), "tokens", 2);
80             return types::Function::Error;
81         }
82         pCharSample = in[1]->getAs<types::String>();
83
84         if (pCharSample->getSize() == 0)
85         {
86             Scierror(999, _("%s: Wrong size for input argument #%d.\n"), "tokens", 2);
87             return types::Function::Error;
88         }
89         sizeSeps = pCharSample->getSize();
90         seps = (wchar_t*)MALLOC((sizeSeps + 1) * sizeof(wchar_t));
91         for (int i = 0; i < sizeSeps ; i++)
92         {
93             int iLen = (int)wcslen(pCharSample->get(i));
94             if (iLen > 1 || iLen < 0)
95             {
96                 Scierror(999, _("%s: Wrong type for input argument #%d: Char(s) expected.\n"), "tokens", 2);
97                 delete pOutString;
98                 FREE(seps);
99                 return types::Function::Error;
100             }
101             seps[i] = pCharSample->get(i)[0];
102         }
103     }
104     else // default delimiters are ' ' and Tabulation
105     {
106         sizeSeps = 2;
107         seps = (wchar_t*)MALLOC((sizeSeps + 1) * sizeof(wchar_t));
108         seps[0] = L' ';
109         seps[1] = L'\t';
110     }
111     seps[sizeSeps] = L'\0';
112
113     // perfom operation
114     int dimsArray[2] = {0, 1};
115     int dims = 2;
116
117     wchar_t** Output_Strings = stringTokens(pString->get(0), seps, &dimsArray[0]);
118     FREE(seps);
119     if (Output_Strings == NULL)
120     {
121         //return empty matrix
122         out.push_back(types::Double::Empty());
123         return types::Function::OK;
124     }
125     else
126     {
127         pOutString  = new types::String(dims, dimsArray);
128         pOutString->set(Output_Strings);
129
130         for (int i = 0 ; i < dimsArray[0] ; i++)
131         {
132             FREE(Output_Strings[i]);
133         }
134         FREE(Output_Strings);
135     }
136
137     out.push_back(pOutString);
138     return types::Function::OK;
139 }
140