Osi 0.107.9

- Main Page
- Related Pages
- Modules
- Namespaces
- Classes
- Files

- File List
- File Members

All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
CoinHelperFunctions.hpp
Go to the documentation of this file.
1 /* $Id: CoinHelperFunctions.hpp 1679 2013-12-05 11:27:45Z forrest $ */
2 // Copyright (C) 2000, International Business Machines
3 // Corporation and others. All Rights Reserved.
4 // This code is licensed under the terms of the Eclipse Public License (EPL).
5
6 #ifndef CoinHelperFunctions_H
7 #define CoinHelperFunctions_H
8
9 #include "CoinUtilsConfig.h"
10
11 #if defined(_MSC_VER)
12 # include <direct.h>
13 # include <cctype>
14 # define getcwd _getcwd
15 # include <cctype>
16 #else
17 # include <unistd.h>
18 #endif
19 //#define USE_MEMCPY
20
21 #include <cstdlib>
22 #include <cstdio>
23 #include <algorithm>
24 #include "CoinTypes.hpp"
25 #include "CoinError.hpp"
26
27 // Compilers can produce better code if they know about __restrict
28 #ifndef COIN_RESTRICT
29 #ifdef COIN_USE_RESTRICT
30 #define COIN_RESTRICT __restrict
31 #else
32 #define COIN_RESTRICT
33 #endif
34 #endif
35
36 //#############################################################################
37
43 template <class T> inline void
44 CoinCopyN(register const T* from, const int size, register T* to)
45 {
46 if (size == 0 || from == to)
47 return;
48
49 #ifndef NDEBUG
50 if (size < 0)
51 throw CoinError("trying to copy negative number of entries",
52 "CoinCopyN", "");
53 #endif
54
55 register int n = (size + 7) / 8;
56 if (to > from) {
57 register const T* downfrom = from + size;
58 register T* downto = to + size;
59 // Use Duff's device to copy
60 switch (size % 8) {
61 case 0: do{ *--downto = *--downfrom;
62 case 7: *--downto = *--downfrom;
63 case 6: *--downto = *--downfrom;
64 case 5: *--downto = *--downfrom;
65 case 4: *--downto = *--downfrom;
66 case 3: *--downto = *--downfrom;
67 case 2: *--downto = *--downfrom;
68 case 1: *--downto = *--downfrom;
69 }while(--n>0);
70 }
71 } else {
72 // Use Duff's device to copy
73 --from;
74 --to;
75 switch (size % 8) {
76 case 0: do{ *++to = *++from;
77 case 7: *++to = *++from;
78 case 6: *++to = *++from;
79 case 5: *++to = *++from;
80 case 4: *++to = *++from;
81 case 3: *++to = *++from;
82 case 2: *++to = *++from;
83 case 1: *++to = *++from;
84 }while(--n>0);
85 }
86 }
87 }
88
89 //-----------------------------------------------------------------------------
90
101 template <class T> inline void
102 CoinCopy(register const T* first, register const T* last, register T* to)
103 {
104 CoinCopyN(first, static_cast<int>(last-first), to);
105 }
106
107 //-----------------------------------------------------------------------------
108
116 template <class T> inline void
117 CoinDisjointCopyN(register const T* from, const int size, register T* to)
118 {
119 #ifndef _MSC_VER
120 if (size == 0 || from == to)
121 return;
122
123 #ifndef NDEBUG
124 if (size < 0)
125 throw CoinError("trying to copy negative number of entries",
126 "CoinDisjointCopyN", "");
127 #endif
128
129 #if 0
130 /* There is no point to do this test. If to and from are from different
131 blocks then dist is undefined, so this can crash correct code. It's
132 better to trust the user that the arrays are really disjoint. */
133 const long dist = to - from;
134 if (-size < dist && dist < size)
135 throw CoinError("overlapping arrays", "CoinDisjointCopyN", "");
136 #endif
137
138 for (register int n = size / 8; n > 0; --n, from += 8, to += 8) {
139 to[0] = from[0];
140 to[1] = from[1];
141 to[2] = from[2];
142 to[3] = from[3];
143 to[4] = from[4];
144 to[5] = from[5];
145 to[6] = from[6];
146 to[7] = from[7];
147 }
148 switch (size % 8) {
149 case 7: to[6] = from[6];
150 case 6: to[5] = from[5];
151 case 5: to[4] = from[4];
152 case 4: to[3] = from[3];
153 case 3: to[2] = from[2];
154 case 2: to[1] = from[1];
155 case 1: to[0] = from[0];
156 case 0: break;
157 }
158 #else
159 CoinCopyN(from, size, to);
160 #endif
161 }
162
163 //-----------------------------------------------------------------------------
164
169 template <class T> inline void
170 CoinDisjointCopy(register const T* first, register const T* last,
171 register T* to)
172 {
173 CoinDisjointCopyN(first, static_cast<int>(last - first), to);
174 }
175
176 //-----------------------------------------------------------------------------
177
182 template <class T> inline T*
183 CoinCopyOfArray( const T * array, const int size)
184 {
185 if (array) {
186 T * arrayNew = new T[size];
187 std::memcpy(arrayNew,array,size*sizeof(T));
188 return arrayNew;
189 } else {
190 return NULL;
191 }
192 }
193
194
199 template <class T> inline T*
200 CoinCopyOfArrayPartial( const T * array, const int size,const int copySize)
201 {
202 if (array||size) {
203 T * arrayNew = new T[size];
204 assert (copySize<=size);
205 std::memcpy(arrayNew,array,copySize*sizeof(T));
206 return arrayNew;
207 } else {
208 return NULL;
209 }
210 }
211
216 template <class T> inline T*
217 CoinCopyOfArray( const T * array, const int size, T value)
218 {
219 T * arrayNew = new T[size];
220 if (array) {
221 std::memcpy(arrayNew,array,size*sizeof(T));
222 } else {
223 int i;
224 for (i=0;i<size;i++)
225 arrayNew[i] = value;
226 }
227 return arrayNew;
228 }
229
230
235 template <class T> inline T*
236 CoinCopyOfArrayOrZero( const T * array , const int size)
237 {
238 T * arrayNew = new T[size];
239 if (array) {
240 std::memcpy(arrayNew,array,size*sizeof(T));
241 } else {
242 std::memset(arrayNew,0,size*sizeof(T));
243 }
244 return arrayNew;
245 }
246
247
248 //-----------------------------------------------------------------------------
249
257 #ifndef COIN_USE_RESTRICT
258 template <class T> inline void
259 CoinMemcpyN(register const T* from, const int size, register T* to)
260 {
261 #ifndef _MSC_VER
262 #ifdef USE_MEMCPY
263 // Use memcpy - seems a lot faster on Intel with gcc
264 #ifndef NDEBUG
265 // Some debug so check
266 if (size < 0)
267 throw CoinError("trying to copy negative number of entries",
268 "CoinMemcpyN", "");
269
270 #if 0
271 /* There is no point to do this test. If to and from are from different
272 blocks then dist is undefined, so this can crash correct code. It's
273 better to trust the user that the arrays are really disjoint. */
274 const long dist = to - from;
275 if (-size < dist && dist < size)
276 throw CoinError("overlapping arrays", "CoinMemcpyN", "");
277 #endif
278 #endif
279 std::memcpy(to,from,size*sizeof(T));
280 #else
281 if (size == 0 || from == to)
282 return;
283
284 #ifndef NDEBUG
285 if (size < 0)
286 throw CoinError("trying to copy negative number of entries",
287 "CoinMemcpyN", "");
288 #endif
289
290 #if 0
291 /* There is no point to do this test. If to and from are from different
292 blocks then dist is undefined, so this can crash correct code. It's
293 better to trust the user that the arrays are really disjoint. */
294 const long dist = to - from;
295 if (-size < dist && dist < size)
296 throw CoinError("overlapping arrays", "CoinMemcpyN", "");
297 #endif
298
299 for (register int n = size / 8; n > 0; --n, from += 8, to += 8) {
300 to[0] = from[0];
301 to[1] = from[1];
302 to[2] = from[2];
303 to[3] = from[3];
304 to[4] = from[4];
305 to[5] = from[5];
306 to[6] = from[6];
307 to[7] = from[7];
308 }
309 switch (size % 8) {
310 case 7: to[6] = from[6];
311 case 6: to[5] = from[5];
312 case 5: to[4] = from[4];
313 case 4: to[3] = from[3];
314 case 3: to[2] = from[2];
315 case 2: to[1] = from[1];
316 case 1: to[0] = from[0];
317 case 0: break;
318 }
319 #endif
320 #else
321 CoinCopyN(from, size, to);
322 #endif
323 }
324 #else
325 template <class T> inline void
326 CoinMemcpyN(const T * COIN_RESTRICT from, int size, T* COIN_RESTRICT to)
327 {
328 #ifdef USE_MEMCPY
329 std::memcpy(to,from,size*sizeof(T));
330 #else
331 T * COIN_RESTRICT put = to;
332 const T * COIN_RESTRICT get = from;
333 for ( ; 0<size ; --size)
334 *put++ = *get++;
335 #endif
336 }
337 #endif
338
339 //-----------------------------------------------------------------------------
340
345 template <class T> inline void
346 CoinMemcpy(register const T* first, register const T* last,
347 register T* to)
348 {
349 CoinMemcpyN(first, static_cast<int>(last - first), to);
350 }
351
352 //#############################################################################
353
360 template <class T> inline void
361 CoinFillN(register T* to, const int size, register const T value)
362 {
363 if (size == 0)
364 return;
365
366 #ifndef NDEBUG
367 if (size < 0)
368 throw CoinError("trying to fill negative number of entries",
369 "CoinFillN", "");
370 #endif
371 #if 1
372 for (register int n = size / 8; n > 0; --n, to += 8) {
373 to[0] = value;
374 to[1] = value;
375 to[2] = value;
376 to[3] = value;
377 to[4] = value;
378 to[5] = value;
379 to[6] = value;
380 to[7] = value;
381 }
382 switch (size % 8) {
383 case 7: to[6] = value;
384 case 6: to[5] = value;
385 case 5: to[4] = value;
386 case 4: to[3] = value;
387 case 3: to[2] = value;
388 case 2: to[1] = value;
389 case 1: to[0] = value;
390 case 0: break;
391 }
392 #else
393 // Use Duff's device to fill
394 register int n = (size + 7) / 8;
395 --to;
396 switch (size % 8) {
397 case 0: do{ *++to = value;
398 case 7: *++to = value;
399 case 6: *++to = value;
400 case 5: *++to = value;
401 case 4: *++to = value;
402 case 3: *++to = value;
403 case 2: *++to = value;
404 case 1: *++to = value;
405 }while(--n>0);
406 }
407 #endif
408 }
409
410 //-----------------------------------------------------------------------------
411
415 template <class T> inline void
416 CoinFill(register T* first, register T* last, const T value)
417 {
418 CoinFillN(first, last - first, value);
419 }
420
421 //#############################################################################
422
429 template <class T> inline void
430 CoinZeroN(register T* to, const int size)
431 {
432 #ifdef USE_MEMCPY
433 // Use memset - seems faster on Intel with gcc
434 #ifndef NDEBUG
435 // Some debug so check
436 if (size < 0)
437 throw CoinError("trying to fill negative number of entries",
438 "CoinZeroN", "");
439 #endif
440 memset(to,0,size*sizeof(T));
441 #else
442 if (size == 0)
443 return;
444
445 #ifndef NDEBUG
446 if (size < 0)
447 throw CoinError("trying to fill negative number of entries",
448 "CoinZeroN", "");
449 #endif
450 #if 1
451 for (register int n = size / 8; n > 0; --n, to += 8) {
452 to[0] = 0;
453 to[1] = 0;
454 to[2] = 0;
455 to[3] = 0;
456 to[4] = 0;
457 to[5] = 0;
458 to[6] = 0;
459 to[7] = 0;
460 }
461 switch (size % 8) {
462 case 7: to[6] = 0;
463 case 6: to[5] = 0;
464 case 5: to[4] = 0;
465 case 4: to[3] = 0;
466 case 3: to[2] = 0;
467 case 2: to[1] = 0;
468 case 1: to[0] = 0;
469 case 0: break;
470 }
471 #else
472 // Use Duff's device to fill
473 register int n = (size + 7) / 8;
474 --to;
475 switch (size % 8) {
476 case 0: do{ *++to = 0;
477 case 7: *++to = 0;
478 case 6: *++to = 0;
479 case 5: *++to = 0;
480 case 4: *++to = 0;
481 case 3: *++to = 0;
482 case 2: *++to = 0;
483 case 1: *++to = 0;
484 }while(--n>0);
485 }
486 #endif
487 #endif
488 }
490 inline void
491 CoinCheckDoubleZero(double * to, const int size)
492 {
493 int n=0;
494 for (int j=0;j<size;j++) {
495 if (to[j])
496 n++;
497 }
498 if (n) {
499 printf("array of length %d should be zero has %d nonzero\n",size,n);
500 }
501 }
503 inline void
504 CoinCheckIntZero(int * to, const int size)
505 {
506 int n=0;
507 for (int j=0;j<size;j++) {
508 if (to[j])
509 n++;
510 }
511 if (n) {
512 printf("array of length %d should be zero has %d nonzero\n",size,n);
513 }
514 }
515
516 //-----------------------------------------------------------------------------
517
521 template <class T> inline void
522 CoinZero(register T* first, register T* last)
523 {
524 CoinZeroN(first, last - first);
525 }
526
527 //#############################################################################
528
530 inline char * CoinStrdup(const char * name)
531 {
532 char* dup = NULL;
533 if (name) {
534 const int len = static_cast<int>(strlen(name));
535 dup = static_cast<char*>(malloc(len+1));
536 CoinMemcpyN(name, len, dup);
537 dup[len] = 0;
538 }
539 return dup;
540 }
541
542 //#############################################################################
543
547 template <class T> inline T
548 CoinMax(register const T x1, register const T x2)
549 {
550 return (x1 > x2) ? x1 : x2;
551 }
552
553 //-----------------------------------------------------------------------------
554
558 template <class T> inline T
559 CoinMin(register const T x1, register const T x2)
560 {
561 return (x1 < x2) ? x1 : x2;
562 }
563
564 //-----------------------------------------------------------------------------
565
569 template <class T> inline T
570 CoinAbs(const T value)
571 {
572 return value<0 ? -value : value;
573 }
574
575 //#############################################################################
576
580 template <class T> inline bool
581 CoinIsSorted(register const T* first, const int size)
582 {
583 if (size == 0)
584 return true;
585
586 #ifndef NDEBUG
587 if (size < 0)
588 throw CoinError("negative number of entries", "CoinIsSorted", "");
589 #endif
590 #if 1
591 // size1 is the number of comparisons to be made
592 const int size1 = size - 1;
593 for (register int n = size1 / 8; n > 0; --n, first += 8) {
594 if (first[8] < first[7]) return false;
595 if (first[7] < first[6]) return false;
596 if (first[6] < first[5]) return false;
597 if (first[5] < first[4]) return false;
598 if (first[4] < first[3]) return false;
599 if (first[3] < first[2]) return false;
600 if (first[2] < first[1]) return false;
601 if (first[1] < first[0]) return false;
602 }
603
604 switch (size1 % 8) {
605 case 7: if (first[7] < first[6]) return false;
606 case 6: if (first[6] < first[5]) return false;
607 case 5: if (first[5] < first[4]) return false;
608 case 4: if (first[4] < first[3]) return false;
609 case 3: if (first[3] < first[2]) return false;
610 case 2: if (first[2] < first[1]) return false;
611 case 1: if (first[1] < first[0]) return false;
612 case 0: break;
613 }
614 #else
615 register const T* next = first;
616 register const T* last = first + size;
617 for (++next; next != last; first = next, ++next)
618 if (*next < *first)
619 return false;
620 #endif
621 return true;
622 }
623
624 //-----------------------------------------------------------------------------
625
629 template <class T> inline bool
630 CoinIsSorted(register const T* first, register const T* last)
631 {
632 return CoinIsSorted(first, static_cast<int>(last - first));
633 }
634
635 //#############################################################################
636
640 template <class T> inline void
641 CoinIotaN(register T* first, const int size, register T init)
642 {
643 if (size == 0)
644 return;
645
646 #ifndef NDEBUG
647 if (size < 0)
648 throw CoinError("negative number of entries", "CoinIotaN", "");
649 #endif
650 #if 1
651 for (register int n = size / 8; n > 0; --n, first += 8, init += 8) {
652 first[0] = init;
653 first[1] = init + 1;
654 first[2] = init + 2;
655 first[3] = init + 3;
656 first[4] = init + 4;
657 first[5] = init + 5;
658 first[6] = init + 6;
659 first[7] = init + 7;
660 }
661 switch (size % 8) {
662 case 7: first[6] = init + 6;
663 case 6: first[5] = init + 5;
664 case 5: first[4] = init + 4;
665 case 4: first[3] = init + 3;
666 case 3: first[2] = init + 2;
667 case 2: first[1] = init + 1;
668 case 1: first[0] = init;
669 case 0: break;
670 }
671 #else
672 // Use Duff's device to fill
673 register int n = (size + 7) / 8;
674 --first;
675 --init;
676 switch (size % 8) {
677 case 0: do{ *++first = ++init;
678 case 7: *++first = ++init;
679 case 6: *++first = ++init;
680 case 5: *++first = ++init;
681 case 4: *++first = ++init;
682 case 3: *++first = ++init;
683 case 2: *++first = ++init;
684 case 1: *++first = ++init;
685 }while(--n>0);
686 }
687 #endif
688 }
689
690 //-----------------------------------------------------------------------------
691
695 template <class T> inline void
696 CoinIota(T* first, const T* last, T init)
697 {
698 CoinIotaN(first, last-first, init);
699 }
700
701 //#############################################################################
702
708 template <class T> inline T *
709 CoinDeleteEntriesFromArray(register T * arrayFirst, register T * arrayLast,
710 const int * firstDelPos, const int * lastDelPos)
711 {
712 int delNum = static_cast<int>(lastDelPos - firstDelPos);
713 if (delNum == 0)
714 return arrayLast;
715
716 if (delNum < 0)
717 throw CoinError("trying to delete negative number of entries",
718 "CoinDeleteEntriesFromArray", "");
719
720 int * delSortedPos = NULL;
721 if (! (CoinIsSorted(firstDelPos, lastDelPos) &&
722 std::adjacent_find(firstDelPos, lastDelPos) == lastDelPos)) {
723 // the positions of the to be deleted is either not sorted or not unique
724 delSortedPos = new int[delNum];
725 CoinDisjointCopy(firstDelPos, lastDelPos, delSortedPos);
726 std::sort(delSortedPos, delSortedPos + delNum);
727 delNum = static_cast<int>(std::unique(delSortedPos,
728 delSortedPos+delNum) - delSortedPos);
729 }
730 const int * delSorted = delSortedPos ? delSortedPos : firstDelPos;
731
732 const int last = delNum - 1;
733 int size = delSorted[0];
734 for (int i = 0; i < last; ++i) {
735 const int copyFirst = delSorted[i] + 1;
736 const int copyLast = delSorted[i+1];
737 CoinCopy(arrayFirst + copyFirst, arrayFirst + copyLast,
738 arrayFirst + size);
739 size += copyLast - copyFirst;
740 }
741 const int copyFirst = delSorted[last] + 1;
742 const int copyLast = static_cast<int>(arrayLast - arrayFirst);
743 CoinCopy(arrayFirst + copyFirst, arrayFirst + copyLast,
744 arrayFirst + size);
745 size += copyLast - copyFirst;
746
747 if (delSortedPos)
748 delete[] delSortedPos;
749
750 return arrayFirst + size;
751 }
752
753 //#############################################################################
754
755 #define COIN_OWN_RANDOM_32
756
757 #if defined COIN_OWN_RANDOM_32
758 /* Thanks to Stefano Gliozzi for providing an operating system
759 independent random number generator. */
760
773 inline double CoinDrand48 (bool isSeed = false, unsigned int seed = 1)
774 {
775 static unsigned int last = 123456;
776 if (isSeed) {
777 last = seed;
778 } else {
779 last = 1664525*last+1013904223;
780 return ((static_cast<double> (last))/4294967296.0);
781 }
782 return (0.0);
783 }
784
786 inline void CoinSeedRandom(int iseed)
787 {
788 CoinDrand48(true, iseed);
789 }
790
791 #else // COIN_OWN_RANDOM_32
792
793 #if defined(_MSC_VER) || defined(__MINGW32__) || defined(__CYGWIN32__)
794
796 inline double CoinDrand48() { return rand() / (double) RAND_MAX; }
798 inline void CoinSeedRandom(int iseed) { srand(iseed + 69822); }
799
800 #else
801
803 inline double CoinDrand48() { return drand48(); }
805 inline void CoinSeedRandom(int iseed) { srand48(iseed + 69822); }
806
807 #endif
808
809 #endif // COIN_OWN_RANDOM_32
810
811 //#############################################################################
812
815 inline char CoinFindDirSeparator()
816 {
817 int size = 1000;
818 char* buf = 0;
819 while (true) {
820 buf = new char[size];
821 if (getcwd(buf, size))
822 break;
823 delete[] buf;
824 buf = 0;
825 size = 2*size;
826 }
827 // if first char is '/' then it's unix and the dirsep is '/'. otherwise we
828 // assume it's dos and the dirsep is '\'
829 char dirsep = buf[0] == '/' ? '/' : '\\';
830 delete[] buf;
831 return dirsep;
832 }
833 //#############################################################################
834
835 inline int CoinStrNCaseCmp(const char* s0, const char* s1,
836 const size_t len)
837 {
838 for (size_t i = 0; i < len; ++i) {
839 if (s0[i] == 0) {
840 return s1[i] == 0 ? 0 : -1;
841 }
842 if (s1[i] == 0) {
843 return 1;
844 }
845 const int c0 = std::tolower(s0[i]);
846 const int c1 = std::tolower(s1[i]);
847 if (c0 < c1)
848 return -1;
849 if (c0 > c1)
850 return 1;
851 }
852 return 0;
853 }
854
855 //#############################################################################
856
858 template <class T> inline void CoinSwap (T &x, T &y)
859 {
860 T t = x;
861 x = y;
862 y = t;
863 }
864
865 //#############################################################################
866
871 template <class T> inline int
872 CoinToFile( const T* array, CoinBigIndex size, FILE * fp)
873 {
874 CoinBigIndex numberWritten;
875 if (array&&size) {
876 numberWritten =
877 static_cast<CoinBigIndex>(fwrite(&size,sizeof(int),1,fp));
878 if (numberWritten!=1)
879 return 1;
880 numberWritten =
881 static_cast<CoinBigIndex>(fwrite(array,sizeof(T),size_t(size),fp));
882 if (numberWritten!=size)
883 return 1;
884 } else {
885 size = 0;
886 numberWritten =
887 static_cast<CoinBigIndex>(fwrite(&size,sizeof(int),1,fp));
888 if (numberWritten!=1)
889 return 1;
890 }
891 return 0;
892 }
893
894 //#############################################################################
895
902 template <class T> inline int
903 CoinFromFile( T* &array, CoinBigIndex size, FILE * fp, CoinBigIndex & newSize)
904 {
905 CoinBigIndex numberRead;
906 numberRead =
907 static_cast<CoinBigIndex>(fread(&newSize,sizeof(int),1,fp));
908 if (numberRead!=1)
909 return 1;
910 int returnCode=0;
911 if (size!=newSize&&(newSize||array))
912 returnCode=2;
913 if (newSize) {
914 array = new T [newSize];
915 numberRead =
916 static_cast<CoinBigIndex>(fread(array,sizeof(T),newSize,fp));
917 if (numberRead!=newSize)
918 returnCode=1;
919 } else {
920 array = NULL;
921 }
922 return returnCode;
923 }
924
925 //#############################################################################
926
928 #if 0
929 inline double CoinCbrt(double x)
930 {
931 #if defined(_MSC_VER)
932 return pow(x,(1./3.));
933 #else
934 return cbrt(x);
935 #endif
936 }
937 #endif
938
939 //-----------------------------------------------------------------------------
940
942 #define CoinSizeofAsInt(type) (static_cast<int>(sizeof(type)))
943 inline int
945 CoinStrlenAsInt(const char * string)
946 {
947 return static_cast<int>(strlen(string));
948 }
949
952 #if defined COIN_OWN_RANDOM_32
953 class CoinThreadRandom {
954 public:
959 CoinThreadRandom()
960 { seed_=12345678;}
962 CoinThreadRandom(int seed)
963 {
964 seed_ = seed;
965 }
967 ~CoinThreadRandom() {}
968 // Copy
969 CoinThreadRandom(const CoinThreadRandom & rhs)
970 { seed_ = rhs.seed_;}
971 // Assignment
972 CoinThreadRandom& operator=(const CoinThreadRandom & rhs)
973 {
974 if (this != &rhs) {
975 seed_ = rhs.seed_;
976 }
977 return *this;
978 }
979
981
986 inline void setSeed(int seed)
987 {
988 seed_ = seed;
989 }
991 inline unsigned int getSeed() const
992 {
993 return seed_;
994 }
996 inline double randomDouble() const
997 {
998 double retVal;
999 seed_ = 1664525*(seed_)+1013904223;
1000 retVal = ((static_cast<double> (seed_))/4294967296.0);
1001 return retVal;
1002 }
1004 inline void randomize(int n=0)
1005 {
1006 if (!n)
1007 n=seed_ & 255;
1008 for (int i=0;i<n;i++)
1009 randomDouble();
1010 }
1012
1013
1014 protected:
1018 mutable unsigned int seed_;
1021 };
1022 #else
1023 class CoinThreadRandom {
1024 public:
1029 CoinThreadRandom()
1030 { seed_[0]=50000;seed_[1]=40000;seed_[2]=30000;}
1032 CoinThreadRandom(const unsigned short seed[3])
1033 { memcpy(seed_,seed,3*sizeof(unsigned short));}
1035 CoinThreadRandom(int seed)
1036 {
1037 union { int i[2]; unsigned short int s[4];} put;
1038 put.i[0]=seed;
1039 put.i[1]=seed;
1040 memcpy(seed_,put.s,3*sizeof(unsigned short));
1041 }
1043 ~CoinThreadRandom() {}
1044 // Copy
1045 CoinThreadRandom(const CoinThreadRandom & rhs)
1046 { memcpy(seed_,rhs.seed_,3*sizeof(unsigned short));}
1047 // Assignment
1048 CoinThreadRandom& operator=(const CoinThreadRandom & rhs)
1049 {
1050 if (this != &rhs) {
1051 memcpy(seed_,rhs.seed_,3*sizeof(unsigned short));
1052 }
1053 return *this;
1054 }
1055
1057
1062 inline void setSeed(const unsigned short seed[3])
1063 { memcpy(seed_,seed,3*sizeof(unsigned short));}
1065 inline void setSeed(int seed)
1066 {
1067 union { int i[2]; unsigned short int s[4];} put;
1068 put.i[0]=seed;
1069 put.i[1]=seed;
1070 memcpy(seed_,put.s,3*sizeof(unsigned short));
1071 }
1073 inline double randomDouble() const
1074 {
1075 double retVal;
1076 #if defined(_MSC_VER) || defined(__MINGW32__) || defined(__CYGWIN32__)
1077 retVal=rand();
1078 retVal=retVal/(double) RAND_MAX;
1079 #else
1080 retVal = erand48(seed_);
1081 #endif
1082 return retVal;
1083 }
1085 inline void randomize(int n=0)
1086 {
1087 if (!n) {
1088 n=seed_[0]+seed_[1]+seed_[2];
1089 n &= 255;
1090 }
1091 for (int i=0;i<n;i++)
1092 randomDouble();
1093 }
1095
1096
1097 protected:
1101 mutable unsigned short seed_[3];
1104 };
1105 #endif
1106 #ifndef COIN_DETAIL
1107 #define COIN_DETAIL_PRINT(s) {}
1108 #else
1109 #define COIN_DETAIL_PRINT(s) s
1110 #endif
1111 #endif
CoinIsSorted
bool CoinIsSorted(register const T *first, const int size)
This helper function tests whether the entries of an array are sorted according to operator&lt;...
Definition: CoinHelperFunctions.hpp:581
CoinError
Error Class thrown by an exception.
Definition: CoinError.hpp:42
CoinThreadRandom::CoinThreadRandom
CoinThreadRandom(const CoinThreadRandom &rhs)
Definition: CoinHelperFunctions.hpp:969
CoinZero
void CoinZero(register T *first, register T *last)
This helper function fills an array with a given value.
Definition: CoinHelperFunctions.hpp:522
CoinDisjointCopyN
void CoinDisjointCopyN(register const T *from, const int size, register T *to)
This helper function copies an array to another location.
Definition: CoinHelperFunctions.hpp:117
CoinThreadRandom::getSeed
unsigned int getSeed() const
Get seed.
Definition: CoinHelperFunctions.hpp:991
CoinSeedRandom
void CoinSeedRandom(int iseed)
Set the seed for the random number generator.
Definition: CoinHelperFunctions.hpp:786
CoinIota
void CoinIota(T *first, const T *last, T init)
This helper function fills an array with the values init, init+1, init+2, etc.
Definition: CoinHelperFunctions.hpp:696
CoinMemcpyN
void CoinMemcpyN(register const T *from, const int size, register T *to)
This helper function copies an array to another location.
Definition: CoinHelperFunctions.hpp:259
CoinFill
void CoinFill(register T *first, register T *last, const T value)
This helper function fills an array with a given value.
Definition: CoinHelperFunctions.hpp:416
CoinMin
T CoinMin(register const T x1, register const T x2)
Return the smaller (according to operator&lt;() of the arguments.
Definition: CoinHelperFunctions.hpp:559
CoinToFile
int CoinToFile(const T *array, CoinBigIndex size, FILE *fp)
This helper function copies an array to file Returns 0 if OK, 1 if bad write.
Definition: CoinHelperFunctions.hpp:872
CoinTypes.hpp
CoinDrand48
double CoinDrand48(bool isSeed=false, unsigned int seed=1)
Return a random number between 0 and 1.
Definition: CoinHelperFunctions.hpp:773
CoinThreadRandom::seed_
unsigned int seed_
Current seed.
Definition: CoinHelperFunctions.hpp:1019
CoinCopyOfArray
T * CoinCopyOfArray(const T *array, const int size)
Return an array of length size filled with input from array, or null if array is null.
Definition: CoinHelperFunctions.hpp:183
CoinStrdup
char * CoinStrdup(const char *name)
Returns strdup or NULL if original NULL.
Definition: CoinHelperFunctions.hpp:530
CoinCheckDoubleZero
void CoinCheckDoubleZero(double *to, const int size)
This Debug helper function checks an array is all zero.
Definition: CoinHelperFunctions.hpp:491
CoinError.hpp
CoinCopyN
void CoinCopyN(register const T *from, const int size, register T *to)
This helper function copies an array to another location using Duff&#39;s device (for a speedup of ~2)...
Definition: CoinHelperFunctions.hpp:44
CoinCheckIntZero
void CoinCheckIntZero(int *to, const int size)
This Debug helper function checks an array is all zero.
Definition: CoinHelperFunctions.hpp:504
CoinSwap
void CoinSwap(T &x, T &y)
Swap the arguments.
Definition: CoinHelperFunctions.hpp:858
CoinThreadRandom::randomize
void randomize(int n=0)
make more random (i.e. for startup)
Definition: CoinHelperFunctions.hpp:1004
COIN_RESTRICT
#define COIN_RESTRICT
Definition: CoinHelperFunctions.hpp:32
CoinMemcpy
void CoinMemcpy(register const T *first, register const T *last, register T *to)
This helper function copies an array to another location.
Definition: CoinHelperFunctions.hpp:346
CoinDisjointCopy
void CoinDisjointCopy(register const T *first, register const T *last, register T *to)
This helper function copies an array to another location.
Definition: CoinHelperFunctions.hpp:170
CoinThreadRandom::CoinThreadRandom
CoinThreadRandom()
Default constructor.
Definition: CoinHelperFunctions.hpp:959
CoinStrNCaseCmp
int CoinStrNCaseCmp(const char *s0, const char *s1, const size_t len)
Definition: CoinHelperFunctions.hpp:835
CoinIotaN
void CoinIotaN(register T *first, const int size, register T init)
This helper function fills an array with the values init, init+1, init+2, etc.
Definition: CoinHelperFunctions.hpp:641
CoinAbs
T CoinAbs(const T value)
Return the absolute value of the argument.
Definition: CoinHelperFunctions.hpp:570
CoinFillN
void CoinFillN(register T *to, const int size, register const T value)
This helper function fills an array with a given value.
Definition: CoinHelperFunctions.hpp:361
CoinFindDirSeparator
char CoinFindDirSeparator()
This function figures out whether file names should contain slashes or backslashes as directory separ...
Definition: CoinHelperFunctions.hpp:815
CoinCopyOfArrayPartial
T * CoinCopyOfArrayPartial(const T *array, const int size, const int copySize)
Return an array of length size filled with first copySize from array, or null if array is null...
Definition: CoinHelperFunctions.hpp:200
CoinDeleteEntriesFromArray
T * CoinDeleteEntriesFromArray(register T *arrayFirst, register T *arrayLast, const int *firstDelPos, const int *lastDelPos)
This helper function deletes certain entries from an array.
Definition: CoinHelperFunctions.hpp:709
CoinZeroN
void CoinZeroN(register T *to, const int size)
This helper function fills an array with zero.
Definition: CoinHelperFunctions.hpp:430
CoinCopyOfArrayOrZero
T * CoinCopyOfArrayOrZero(const T *array, const int size)
Return an array of length size filled with input from array, or filled with zero if array is null...
Definition: CoinHelperFunctions.hpp:236
CoinThreadRandom::setSeed
void setSeed(int seed)
Set seed.
Definition: CoinHelperFunctions.hpp:986
CoinStrlenAsInt
int CoinStrlenAsInt(const char *string)
This helper returns &quot;strlen&quot; as an int.
Definition: CoinHelperFunctions.hpp:945
CoinBigIndex
int CoinBigIndex
Definition: Coin_C_defines.h:105
CoinThreadRandom::operator=
CoinThreadRandom & operator=(const CoinThreadRandom &rhs)
Definition: CoinHelperFunctions.hpp:972
CoinThreadRandom::~CoinThreadRandom
~CoinThreadRandom()
Destructor.
Definition: CoinHelperFunctions.hpp:967
CoinFromFile
int CoinFromFile(T *&array, CoinBigIndex size, FILE *fp, CoinBigIndex &newSize)
This helper function copies an array from file and creates with new.
Definition: CoinHelperFunctions.hpp:903
CoinMax
T CoinMax(register const T x1, register const T x2)
Return the larger (according to operator&lt;() of the arguments.
Definition: CoinHelperFunctions.hpp:548
CoinThreadRandom::randomDouble
double randomDouble() const
return a random number
Definition: CoinHelperFunctions.hpp:996
CoinCopy
void CoinCopy(register const T *first, register const T *last, register T *to)
This helper function copies an array to another location using Duff&#39;s device (for a speedup of ~2)...
Definition: CoinHelperFunctions.hpp:102
CoinUtilsConfig.h
CoinThreadRandom::CoinThreadRandom
CoinThreadRandom(int seed)
Constructor wih seed.
Definition: CoinHelperFunctions.hpp:962
CoinThreadRandom
Class for thread specific random numbers.
Definition: CoinHelperFunctions.hpp:953