OSMathUtil.cpp
Go to the documentation of this file.
1 /* $Id: OSMathUtil.cpp 5284 2017-12-08 13:52:50Z stefan $ */
19 #include "OSConfig.h"
20 #include "OSMathUtil.h"
21 #include "OSParameters.h"
22 #include "OSGeneral.h"
23 
24 #ifdef HAVE_CSTDLIB
25 # include <cstdlib>
26 #else
27 # ifdef HAVE_STDLIB_H
28 # include <stdlib.h>
29 # endif
30 #endif
31 
32 #ifdef HAVE_CSTRING
33 # include <cstring>
34 #else
35 # ifdef HAVE_STRING_H
36 # include <string.h>
37 # else
38 # error "don't have header file for string"
39 # endif
40 #endif
41 
42 #include <iostream>
43 #include <sstream>
44 
45 using std::ostringstream;
46 
47 
49 {
50 }
51 
53 {
54 }
55 
56 
58  bool isColumnMajor, int startSize, int valueSize, int* start, int* index,
59  double* value, int dimension)
60 {
61  if ( !start || startSize <= 1 ) return NULL;
62  if ( !value || !index ) return NULL;
63 
64  int iStartSize = dimension + 1;
65  SparseMatrix *matrix ;
66  matrix = new SparseMatrix( !isColumnMajor, iStartSize, valueSize);
67  int i,j, iTemp;
68  int iNumSource = startSize - 1;
69  int* miStart = matrix->starts;
70  int* miIndex = matrix->indexes;
71  double* mdValue = matrix->values;
72 
73  for ( i = 0; i < iStartSize; i++)
74  {
75  miStart [ i ] = 0;
76  }
77  // for illustration assume we are converting from column to row major
78  // i is indexing columns (variables) and j is indexing row numbers
79  for (i = 0; i < iNumSource; i++)
80  {
81  for (j = start[i]; j < start[ i + 1 ]; j++)
82  {
83  // index[ j] is a row index, we have just found an occurance of row index[j]
84  // therefore we increase by 1 (or push back) the start of the row indexed by index[j] + 1,
85  // i.e. the start of the next row
86  miStart[ index[j] + 1] ++;
87  }
88  }
89  // at this point, miStart[ i] holds the number of columns with a nonzero in row i - 1
90  // we are not done with the start indices, if we are here, and we
91  // knew the correct starting point of row i -1, the correct starting point
92  // for row i is miStart[i] + miStart [i - 1]
93  miStart[0] = 0;
94  for (i = 1; i < iStartSize; i++ )
95  {
96  miStart[i] += miStart [i - 1] ;
97  }
98 
99  // now get the correct values
100  // again assume we are converting column major to row major
101  // loop over columns
102  for (i = 0; i < iNumSource; i++)
103  {
104  // get row indices and values of the A matrix
105  for (j = start[i]; j < start[ i + 1 ]; j++)
106  {
107  iTemp = miStart[ index[j]];
108  miIndex [ iTemp] = i;
109  mdValue [ iTemp] = value[j];
110  miStart[ index[j]] ++;
111  }
112  }
113 
114  // miStart[ i] is now equal to miStart[ i + 1], so readjust
115  for (i = iStartSize - 1; i >= 1; i-- )
116  {
117  miStart[i] = miStart [i - 1] ;
118  }
119 
120  miStart[0] = 0;
121  return matrix;
122 }//convertLinearConstraintCoefficientMatrixToTheOtherMajor
123 
124 
125 double os_strtod_wrap(const char *str, char **strEnd)
126 {
127 /* Deal with some special cases first, which are needed
128  * for the parsers (and schemas) to work properly
129  */
130  if (strcmp(str, "INF") == 0)
131  {
132  *strEnd = (char *)str + 3;
133  return OSDBL_MAX;
134  }
135  else if (strcmp(str,"-INF") == 0)
136  {
137  *strEnd = (char *)str + 4;
138  return -OSDBL_MAX;
139  }
140  else if (strcmp(str, "NaN") == 0)
141  {
142  *strEnd = (char *)str + 3;
143  return OSNaN();
144  }
145  else
146 #ifndef USE_DTOA
147  return strtod(str, strEnd);
148 #else
149  return os_strtod(str, strEnd);
150 #endif
151 }//end os_strtod_wrap
152 
153 
154 std::string os_dtoa_format(double x)
155 {
156 /* Deal with some special cases first, which must be rendered
157  * precisely (case-sensitive) for the parsers to work properly
158  */
159  ostringstream outStr;
160  if (x == OSDBL_MAX)
161  {
162  outStr << "INF";
163  return outStr.str();
164  }
165  if (x == -OSDBL_MAX)
166  {
167  outStr << "-INF";
168  return outStr.str();
169  }
170  if ( OSIsnan(x) )
171  {
172  outStr << "NaN";
173  return outStr.str();
174  }
175 #ifndef USE_DTOA
176  outStr << x;
177  return outStr.str();
178 #else
179  outStr << "";
180  char *charResult;
181  int decimalPointPos;
182  int sign;
183  int strLength = 0;
184  int k = 0;
185  charResult = os_dtoa(x, 0, 0, &decimalPointPos, &sign, NULL);
186  // get the length
187  // get the sign, 1 for negative
188  if( sign == 1) outStr << "-";
189  strLength = strlen( charResult);
190 
191 
192  // return charResult if we have nan or infinity -- if so, return original string
193  if(decimalPointPos == 9999)
194  {
195  for(k = 0; k < strLength; k++)outStr << charResult[ k];
196  return outStr.str();
197  }
198  if(decimalPointPos == strLength) //don't we have an integer?
199  {
200  for(k = 0; k < strLength; k++)outStr << charResult[ k];
201  return outStr.str();
202  }
203  if(decimalPointPos >= 0)
204  {
205  if(decimalPointPos > strLength)
206  {
207  if(strLength == 1)
208  {
209  // put in all of the characters from charResult
210  outStr << charResult[ 0];
211  if(decimalPointPos <= 5) //hey for more than 5 zeros go for e notation
212  {
213  for(k = strLength; k < decimalPointPos; k++) outStr << "0";
214  }
215  else
216  {
217  outStr << ".";
218  for(k = 1; k < strLength; k++) outStr << charResult[ k];
219  outStr << "e";
220  outStr << decimalPointPos - 1;
221  }
222  }
223  else
224  {
225  outStr << charResult[ 0];
226  outStr << ".";
227  for(k = 1; k < strLength; k++) outStr << charResult[ k];
228  outStr << "e";
229  outStr << decimalPointPos - 1;
230  }
231  }
232  else
233  {
234  for(k = 0; k < decimalPointPos; k++) outStr << charResult[ k];
235  outStr << ".";
236  for(k = decimalPointPos; k < strLength; k++) outStr << charResult[ k];
237  }
238  }
239  else
240  {
241  outStr << charResult[ 0];
242  outStr << ".";
243  //for(k = 0; k < -decimalPointPos; k++) outStr << "0";
244  for(k = 1; k < strLength; k++)outStr << charResult[ k];
245  outStr << "e";
246  outStr << decimalPointPos -1 ;
247  }
248  //
249  os_freedtoa( charResult);
250  return outStr.str();
251 #endif
252 }// end os_dtoa_format
253 
254 
262 double OSRand()
263 {
264  int i;
265 
266  i = rand();
267 
268  return (double) i/RAND_MAX;
269 }
270 
271 
279 double OSiRand(int iMin, int iMax)
280 {
281  return iMin + rand()%(iMax - iMin + 1);
282 }
283 
284 
double os_strtod(const char *s00, char **se)
Definition: OSdtoa.cpp:2541
static SparseMatrix * convertLinearConstraintCoefficientMatrixToTheOtherMajor(bool isColumnMajor, int startSize, int valueSize, int *start, int *index, double *value, int dimension)
Round a double number to the precision specified.
Definition: OSMathUtil.cpp:57
void os_freedtoa(char *s)
double OSRand()
OSRand()
Definition: OSMathUtil.cpp:262
static char * j
Definition: OSdtoa.cpp:3622
double os_strtod_wrap(const char *str, char **strEnd)
Definition: OSMathUtil.cpp:125
~MathUtil()
the class destructor
Definition: OSMathUtil.cpp:52
int * indexes
indexes holds an integer array of rowIdx (or colIdx) elements in coefMatrix (AMatrix).
Definition: OSGeneral.h:258
double OSNaN()
returns the value for NaN used in OS
double OSiRand(int iMin, int iMax)
OSiRand(int iMin, int iMax)
Definition: OSMathUtil.cpp:279
a sparse matrix data structure
Definition: OSGeneral.h:223
void fint fint * k
const double OSDBL_MAX
Definition: OSParameters.h:93
double * values
values holds a double array of value elements in coefMatrix (AMatrix), which contains nonzero element...
Definition: OSGeneral.h:264
MathUtil()
the class constructor
Definition: OSMathUtil.cpp:48
char * os_dtoa(double dd, int mode, int ndigits, int *decpt, int *sign, char **rve)
Definition: OSdtoa.cpp:3714
std::string os_dtoa_format(double x)
Definition: OSMathUtil.cpp:154
int * starts
starts holds an integer array of start elements in coefMatrix (AMatrix), which points to the start of...
Definition: OSGeneral.h:252
bool OSIsnan(double x)
checks whether a given double is NaN
void fint fint fint real fint real * x