1 // The template and inlines for the -*- C++ -*- valarray class. 2 3 // Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002 4 // Free Software Foundation, Inc. 5 // 6 // This file is part of the GNU ISO C++ Library. This library is free 7 // software; you can redistribute it and/or modify it under the 8 // terms of the GNU General Public License as published by the 9 // Free Software Foundation; either version 2, or (at your option) 10 // any later version. 11 12 // This library is distributed in the hope that it will be useful, 13 // but WITHOUT ANY WARRANTY; without even the implied warranty of 14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 // GNU General Public License for more details. 16 17 // You should have received a copy of the GNU General Public License along 18 // with this library; see the file COPYING. If not, write to the Free 19 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, 20 // USA. 21 22 // As a special exception, you may use this file as part of a free software 23 // library without restriction. Specifically, if other files instantiate 24 // templates or use macros or inline functions from this file, or you compile 25 // this file and link it with other files to produce an executable, this 26 // file does not by itself cause the resulting executable to be covered by 27 // the GNU General Public License. This exception does not however 28 // invalidate any other reasons why the executable file might be covered by 29 // the GNU General Public License. 30 31 // Written by Gabriel Dos Reis <Gabriel.Dos-Reis@DPTMaths.ENS-Cachan.Fr> 32 33 /** @file valarray 34 * This is a Standard C++ Library header. You should @c #include this header 35 * in your programs, rather than any of the "st[dl]_*.h" implementation files. 36 */ 37 38 #ifndef _CPP_VALARRAY 39 #define _CPP_VALARRAY 1 40 41 #pragma GCC system_header 42 43 #include <bits/c++config.h> 44 #include <cstddef> 45 #include <cmath> 46 #include <cstdlib> 47 #include <numeric> 48 #include <algorithm> 49 50 namespace std 51 { 52 template<class _Clos, typename _Tp> 53 class _Expr; 54 55 template<typename _Tp1, typename _Tp2> 56 class _ValArray; 57 58 template<class _Oper, template<class, class> class _Meta, class _Dom> 59 struct _UnClos; 60 61 template<class _Oper, 62 template<class, class> class _Meta1, 63 template<class, class> class _Meta2, 64 class _Dom1, class _Dom2> 65 class _BinClos; 66 67 template<template<class, class> class _Meta, class _Dom> 68 class _SClos; 69 70 template<template<class, class> class _Meta, class _Dom> 71 class _GClos; 72 73 template<template<class, class> class _Meta, class _Dom> 74 class _IClos; 75 76 template<template<class, class> class _Meta, class _Dom> 77 class _ValFunClos; 78 79 template<template<class, class> class _Meta, class _Dom> 80 class _RefFunClos; 81 82 template<class _Tp> class valarray; // An array of type _Tp 83 class slice; // BLAS-like slice out of an array 84 template<class _Tp> class slice_array; 85 class gslice; // generalized slice out of an array 86 template<class _Tp> class gslice_array; 87 template<class _Tp> class mask_array; // masked array 88 template<class _Tp> class indirect_array; // indirected array 89 90 } // namespace std 91 92 #include <bits/valarray_array.h> 93 #include <bits/valarray_meta.h> 94 95 namespace std 96 { 97 template<class _Tp> 98 class valarray 99 { 100 template<class _Op> 101 struct _UnaryOp 102 { 103 typedef typename __fun<_Op, _Tp>::result_type __rt; 104 typedef _Expr<_UnClos<_Op, _ValArray, _Tp>, __rt> _Rt; 105 }; 106 public: 107 typedef _Tp value_type; 108 109 // _lib.valarray.cons_ construct/destroy: 110 valarray(); 111 explicit valarray(size_t); 112 valarray(const _Tp&, size_t); 113 valarray(const _Tp* __restrict__, size_t); 114 valarray(const valarray&); 115 valarray(const slice_array<_Tp>&); 116 valarray(const gslice_array<_Tp>&); 117 valarray(const mask_array<_Tp>&); 118 valarray(const indirect_array<_Tp>&); 119 template<class _Dom> 120 valarray(const _Expr<_Dom,_Tp>& __e); 121 ~valarray(); 122 123 // _lib.valarray.assign_ assignment: 124 valarray<_Tp>& operator=(const valarray<_Tp>&); 125 valarray<_Tp>& operator=(const _Tp&); 126 valarray<_Tp>& operator=(const slice_array<_Tp>&); 127 valarray<_Tp>& operator=(const gslice_array<_Tp>&); 128 valarray<_Tp>& operator=(const mask_array<_Tp>&); 129 valarray<_Tp>& operator=(const indirect_array<_Tp>&); 130 131 template<class _Dom> valarray<_Tp>& 132 operator= (const _Expr<_Dom,_Tp>&); 133 134 // _lib.valarray.access_ element access: 135 // XXX: LWG to be resolved. 136 const _Tp& operator[](size_t) const; 137 _Tp& operator[](size_t); 138 // _lib.valarray.sub_ subset operations: 139 _Expr<_SClos<_ValArray,_Tp>, _Tp> operator[](slice) const; 140 slice_array<_Tp> operator[](slice); 141 _Expr<_GClos<_ValArray,_Tp>, _Tp> operator[](const gslice&) const; 142 gslice_array<_Tp> operator[](const gslice&); 143 valarray<_Tp> operator[](const valarray<bool>&) const; 144 mask_array<_Tp> operator[](const valarray<bool>&); 145 _Expr<_IClos<_ValArray, _Tp>, _Tp> 146 operator[](const valarray<size_t>&) const; 147 indirect_array<_Tp> operator[](const valarray<size_t>&); 148 149 // _lib.valarray.unary_ unary operators: 150 typename _UnaryOp<__unary_plus>::_Rt operator+() const; 151 typename _UnaryOp<__negate>::_Rt operator-() const; 152 typename _UnaryOp<__bitwise_not>::_Rt operator~() const; 153 typename _UnaryOp<__logical_not>::_Rt operator!() const; 154 155 // _lib.valarray.cassign_ computed assignment: 156 valarray<_Tp>& operator*=(const _Tp&); 157 valarray<_Tp>& operator/=(const _Tp&); 158 valarray<_Tp>& operator%=(const _Tp&); 159 valarray<_Tp>& operator+=(const _Tp&); 160 valarray<_Tp>& operator-=(const _Tp&); 161 valarray<_Tp>& operator^=(const _Tp&); 162 valarray<_Tp>& operator&=(const _Tp&); 163 valarray<_Tp>& operator|=(const _Tp&); 164 valarray<_Tp>& operator<<=(const _Tp&); 165 valarray<_Tp>& operator>>=(const _Tp&); 166 valarray<_Tp>& operator*=(const valarray<_Tp>&); 167 valarray<_Tp>& operator/=(const valarray<_Tp>&); 168 valarray<_Tp>& operator%=(const valarray<_Tp>&); 169 valarray<_Tp>& operator+=(const valarray<_Tp>&); 170 valarray<_Tp>& operator-=(const valarray<_Tp>&); 171 valarray<_Tp>& operator^=(const valarray<_Tp>&); 172 valarray<_Tp>& operator|=(const valarray<_Tp>&); 173 valarray<_Tp>& operator&=(const valarray<_Tp>&); 174 valarray<_Tp>& operator<<=(const valarray<_Tp>&); 175 valarray<_Tp>& operator>>=(const valarray<_Tp>&); 176 177 template<class _Dom> 178 valarray<_Tp>& operator*=(const _Expr<_Dom,_Tp>&); 179 template<class _Dom> 180 valarray<_Tp>& operator/=(const _Expr<_Dom,_Tp>&); 181 template<class _Dom> 182 valarray<_Tp>& operator%=(const _Expr<_Dom,_Tp>&); 183 template<class _Dom> 184 valarray<_Tp>& operator+=(const _Expr<_Dom,_Tp>&); 185 template<class _Dom> 186 valarray<_Tp>& operator-=(const _Expr<_Dom,_Tp>&); 187 template<class _Dom> 188 valarray<_Tp>& operator^=(const _Expr<_Dom,_Tp>&); 189 template<class _Dom> 190 valarray<_Tp>& operator|=(const _Expr<_Dom,_Tp>&); 191 template<class _Dom> 192 valarray<_Tp>& operator&=(const _Expr<_Dom,_Tp>&); 193 template<class _Dom> 194 valarray<_Tp>& operator<<=(const _Expr<_Dom,_Tp>&); 195 template<class _Dom> 196 valarray<_Tp>& operator>>=(const _Expr<_Dom,_Tp>&); 197 198 199 // _lib.valarray.members_ member functions: 200 size_t size() const; 201 _Tp sum() const; 202 _Tp min() const; 203 _Tp max() const; 204 205 // // FIXME: Extension 206 // _Tp product () const; 207 208 valarray<_Tp> shift (int) const; 209 valarray<_Tp> cshift(int) const; 210 _Expr<_ValFunClos<_ValArray,_Tp>,_Tp> apply(_Tp func(_Tp)) const; 211 _Expr<_RefFunClos<_ValArray,_Tp>,_Tp> apply(_Tp func(const _Tp&)) const; 212 void resize(size_t __size, _Tp __c = _Tp()); 213 214 private: 215 size_t _M_size; 216 _Tp* __restrict__ _M_data; 217 218 friend class _Array<_Tp>; 219 }; 220 221 template<typename _Tp> 222 inline const _Tp& 223 valarray<_Tp>::operator[](size_t __i) const 224 { return _M_data[__i]; } 225 226 template<typename _Tp> 227 inline _Tp& 228 valarray<_Tp>::operator[](size_t __i) 229 { return _M_data[__i]; } 230 231 } // std:: 232 233 #include <bits/slice_array.h> 234 #include <bits/gslice.h> 235 #include <bits/gslice_array.h> 236 #include <bits/mask_array.h> 237 #include <bits/indirect_array.h> 238 239 namespace std 240 { 241 template<typename _Tp> 242 inline valarray()243 valarray<_Tp>::valarray() : _M_size(0), _M_data(0) {} 244 245 template<typename _Tp> 246 inline valarray(size_t __n)247 valarray<_Tp>::valarray(size_t __n) 248 : _M_size(__n), _M_data(__valarray_get_storage<_Tp>(__n)) 249 { __valarray_default_construct(_M_data, _M_data + __n); } 250 251 template<typename _Tp> 252 inline valarray(const _Tp & __t,size_t __n)253 valarray<_Tp>::valarray(const _Tp& __t, size_t __n) 254 : _M_size(__n), _M_data(__valarray_get_storage<_Tp>(__n)) 255 { __valarray_fill_construct(_M_data, _M_data + __n, __t); } 256 257 template<typename _Tp> 258 inline valarray(const _Tp * __restrict__ __p,size_t __n)259 valarray<_Tp>::valarray(const _Tp* __restrict__ __p, size_t __n) 260 : _M_size(__n), _M_data(__valarray_get_storage<_Tp>(__n)) 261 { __valarray_copy_construct(__p, __p + __n, _M_data); } 262 263 template<typename _Tp> 264 inline valarray(const valarray<_Tp> & __v)265 valarray<_Tp>::valarray(const valarray<_Tp>& __v) 266 : _M_size(__v._M_size), _M_data(__valarray_get_storage<_Tp>(__v._M_size)) 267 { __valarray_copy_construct(__v._M_data, __v._M_data + _M_size, _M_data); } 268 269 template<typename _Tp> 270 inline valarray(const slice_array<_Tp> & __sa)271 valarray<_Tp>::valarray(const slice_array<_Tp>& __sa) 272 : _M_size(__sa._M_sz), _M_data(__valarray_get_storage<_Tp>(__sa._M_sz)) 273 { 274 __valarray_copy 275 (__sa._M_array, __sa._M_sz, __sa._M_stride, _Array<_Tp>(_M_data)); 276 } 277 278 template<typename _Tp> 279 inline valarray(const gslice_array<_Tp> & __ga)280 valarray<_Tp>::valarray(const gslice_array<_Tp>& __ga) 281 : _M_size(__ga._M_index.size()), 282 _M_data(__valarray_get_storage<_Tp>(_M_size)) 283 { 284 __valarray_copy 285 (__ga._M_array, _Array<size_t>(__ga._M_index), 286 _Array<_Tp>(_M_data), _M_size); 287 } 288 289 template<typename _Tp> 290 inline valarray(const mask_array<_Tp> & __ma)291 valarray<_Tp>::valarray(const mask_array<_Tp>& __ma) 292 : _M_size(__ma._M_sz), _M_data(__valarray_get_storage<_Tp>(__ma._M_sz)) 293 { 294 __valarray_copy 295 (__ma._M_array, __ma._M_mask, _Array<_Tp>(_M_data), _M_size); 296 } 297 298 template<typename _Tp> 299 inline valarray(const indirect_array<_Tp> & __ia)300 valarray<_Tp>::valarray(const indirect_array<_Tp>& __ia) 301 : _M_size(__ia._M_sz), _M_data(__valarray_get_storage<_Tp>(__ia._M_sz)) 302 { 303 __valarray_copy 304 (__ia._M_array, __ia._M_index, _Array<_Tp>(_M_data), _M_size); 305 } 306 307 template<typename _Tp> template<class _Dom> 308 inline valarray(const _Expr<_Dom,_Tp> & __e)309 valarray<_Tp>::valarray(const _Expr<_Dom, _Tp>& __e) 310 : _M_size(__e.size()), _M_data(__valarray_get_storage<_Tp>(_M_size)) 311 { __valarray_copy(__e, _M_size, _Array<_Tp>(_M_data)); } 312 313 template<typename _Tp> 314 inline ~valarray()315 valarray<_Tp>::~valarray() 316 { 317 __valarray_destroy_elements(_M_data, _M_data + _M_size); 318 __valarray_release_memory(_M_data); 319 } 320 321 template<typename _Tp> 322 inline valarray<_Tp>& 323 valarray<_Tp>::operator=(const valarray<_Tp>& __v) 324 { 325 __valarray_copy(__v._M_data, _M_size, _M_data); 326 return *this; 327 } 328 329 template<typename _Tp> 330 inline valarray<_Tp>& 331 valarray<_Tp>::operator=(const _Tp& __t) 332 { 333 __valarray_fill(_M_data, _M_size, __t); 334 return *this; 335 } 336 337 template<typename _Tp> 338 inline valarray<_Tp>& 339 valarray<_Tp>::operator=(const slice_array<_Tp>& __sa) 340 { 341 __valarray_copy(__sa._M_array, __sa._M_sz, 342 __sa._M_stride, _Array<_Tp>(_M_data)); 343 return *this; 344 } 345 346 template<typename _Tp> 347 inline valarray<_Tp>& 348 valarray<_Tp>::operator=(const gslice_array<_Tp>& __ga) 349 { 350 __valarray_copy(__ga._M_array, _Array<size_t>(__ga._M_index), 351 _Array<_Tp>(_M_data), _M_size); 352 return *this; 353 } 354 355 template<typename _Tp> 356 inline valarray<_Tp>& 357 valarray<_Tp>::operator=(const mask_array<_Tp>& __ma) 358 { 359 __valarray_copy(__ma._M_array, __ma._M_mask, 360 _Array<_Tp>(_M_data), _M_size); 361 return *this; 362 } 363 364 template<typename _Tp> 365 inline valarray<_Tp>& 366 valarray<_Tp>::operator=(const indirect_array<_Tp>& __ia) 367 { 368 __valarray_copy(__ia._M_array, __ia._M_index, 369 _Array<_Tp>(_M_data), _M_size); 370 return *this; 371 } 372 373 template<typename _Tp> template<class _Dom> 374 inline valarray<_Tp>& 375 valarray<_Tp>::operator=(const _Expr<_Dom, _Tp>& __e) 376 { 377 __valarray_copy(__e, _M_size, _Array<_Tp>(_M_data)); 378 return *this; 379 } 380 381 template<typename _Tp> 382 inline _Expr<_SClos<_ValArray,_Tp>, _Tp> 383 valarray<_Tp>::operator[](slice __s) const 384 { 385 typedef _SClos<_ValArray,_Tp> _Closure; 386 return _Expr<_Closure, _Tp>(_Closure (_Array<_Tp>(_M_data), __s)); 387 } 388 389 template<typename _Tp> 390 inline slice_array<_Tp> 391 valarray<_Tp>::operator[](slice __s) 392 { 393 return slice_array<_Tp>(_Array<_Tp>(_M_data), __s); 394 } 395 396 template<typename _Tp> 397 inline _Expr<_GClos<_ValArray,_Tp>, _Tp> 398 valarray<_Tp>::operator[](const gslice& __gs) const 399 { 400 typedef _GClos<_ValArray,_Tp> _Closure; 401 return _Expr<_Closure, _Tp> 402 (_Closure(_Array<_Tp>(_M_data), __gs._M_index->_M_index)); 403 } 404 405 template<typename _Tp> 406 inline gslice_array<_Tp> 407 valarray<_Tp>::operator[](const gslice& __gs) 408 { 409 return gslice_array<_Tp> 410 (_Array<_Tp>(_M_data), __gs._M_index->_M_index); 411 } 412 413 template<typename _Tp> 414 inline valarray<_Tp> 415 valarray<_Tp>::operator[](const valarray<bool>& __m) const 416 { 417 size_t __s = 0; 418 size_t __e = __m.size(); 419 for (size_t __i=0; __i<__e; ++__i) 420 if (__m[__i]) ++__s; 421 return valarray<_Tp>(mask_array<_Tp>(_Array<_Tp>(_M_data), __s, 422 _Array<bool> (__m))); 423 } 424 425 template<typename _Tp> 426 inline mask_array<_Tp> 427 valarray<_Tp>::operator[](const valarray<bool>& __m) 428 { 429 size_t __s = 0; 430 size_t __e = __m.size(); 431 for (size_t __i=0; __i<__e; ++__i) 432 if (__m[__i]) ++__s; 433 return mask_array<_Tp>(_Array<_Tp>(_M_data), __s, _Array<bool>(__m)); 434 } 435 436 template<typename _Tp> 437 inline _Expr<_IClos<_ValArray,_Tp>, _Tp> 438 valarray<_Tp>::operator[](const valarray<size_t>& __i) const 439 { 440 typedef _IClos<_ValArray,_Tp> _Closure; 441 return _Expr<_Closure, _Tp>(_Closure(*this, __i)); 442 } 443 444 template<typename _Tp> 445 inline indirect_array<_Tp> 446 valarray<_Tp>::operator[](const valarray<size_t>& __i) 447 { 448 return indirect_array<_Tp>(_Array<_Tp>(_M_data), __i.size(), 449 _Array<size_t>(__i)); 450 } 451 452 template<class _Tp> 453 inline size_t size()454 valarray<_Tp>::size() const 455 { return _M_size; } 456 457 template<class _Tp> 458 inline _Tp sum()459 valarray<_Tp>::sum() const 460 { 461 return __valarray_sum(_M_data, _M_data + _M_size); 462 } 463 464 // template<typename _Tp> 465 // inline _Tp 466 // valarray<_Tp>::product () const 467 // { 468 // return __valarray_product(_M_data, _M_data + _M_size); 469 // } 470 471 template <class _Tp> 472 inline valarray<_Tp> shift(int __n)473 valarray<_Tp>::shift(int __n) const 474 { 475 _Tp* const __a = static_cast<_Tp*> 476 (__builtin_alloca(sizeof(_Tp) * _M_size)); 477 if (__n == 0) // no shift 478 __valarray_copy_construct(_M_data, _M_data + _M_size, __a); 479 else if (__n > 0) // __n > 0: shift left 480 { 481 if (size_t(__n) > _M_size) 482 __valarray_default_construct(__a, __a + __n); 483 else 484 { 485 __valarray_copy_construct(_M_data+__n, _M_data + _M_size, __a); 486 __valarray_default_construct(__a+_M_size-__n, __a + _M_size); 487 } 488 } 489 else // __n < 0: shift right 490 { 491 __valarray_copy_construct (_M_data, _M_data+_M_size+__n, __a-__n); 492 __valarray_default_construct(__a, __a - __n); 493 } 494 return valarray<_Tp> (__a, _M_size); 495 } 496 497 template <class _Tp> 498 inline valarray<_Tp> cshift(int __n)499 valarray<_Tp>::cshift (int __n) const 500 { 501 _Tp* const __a = static_cast<_Tp*> 502 (__builtin_alloca (sizeof(_Tp) * _M_size)); 503 if (__n == 0) // no cshift 504 __valarray_copy_construct(_M_data, _M_data + _M_size, __a); 505 else if (__n > 0) // cshift left 506 { 507 __valarray_copy_construct(_M_data, _M_data+__n, __a+_M_size-__n); 508 __valarray_copy_construct(_M_data+__n, _M_data + _M_size, __a); 509 } 510 else // cshift right 511 { 512 __valarray_copy_construct 513 (_M_data + _M_size+__n, _M_data + _M_size, __a); 514 __valarray_copy_construct 515 (_M_data, _M_data + _M_size+__n, __a - __n); 516 } 517 return valarray<_Tp>(__a, _M_size); 518 } 519 520 template <class _Tp> 521 inline void resize(size_t __n,_Tp __c)522 valarray<_Tp>::resize (size_t __n, _Tp __c) 523 { 524 // This complication is so to make valarray<valarray<T> > work 525 // even though it is not required by the standard. Nobody should 526 // be saying valarray<valarray<T> > anyway. See the specs. 527 __valarray_destroy_elements(_M_data, _M_data + _M_size); 528 if (_M_size != __n) 529 { 530 __valarray_release_memory(_M_data); 531 _M_size = __n; 532 _M_data = __valarray_get_storage<_Tp>(__n); 533 } 534 __valarray_fill_construct(_M_data, _M_data + __n, __c); 535 } 536 537 template<typename _Tp> 538 inline _Tp min()539 valarray<_Tp>::min() const 540 { 541 return *min_element (_M_data, _M_data+_M_size); 542 } 543 544 template<typename _Tp> 545 inline _Tp max()546 valarray<_Tp>::max() const 547 { 548 return *max_element (_M_data, _M_data+_M_size); 549 } 550 551 template<class _Tp> 552 inline _Expr<_ValFunClos<_ValArray,_Tp>,_Tp> apply(_Tp func (_Tp))553 valarray<_Tp>::apply(_Tp func(_Tp)) const 554 { 555 typedef _ValFunClos<_ValArray,_Tp> _Closure; 556 return _Expr<_Closure,_Tp>(_Closure(*this, func)); 557 } 558 559 template<class _Tp> 560 inline _Expr<_RefFunClos<_ValArray,_Tp>,_Tp> apply(_Tp func (const _Tp &))561 valarray<_Tp>::apply(_Tp func(const _Tp &)) const 562 { 563 typedef _RefFunClos<_ValArray,_Tp> _Closure; 564 return _Expr<_Closure,_Tp>(_Closure(*this, func)); 565 } 566 567 #define _DEFINE_VALARRAY_UNARY_OPERATOR(_Op, _Name) \ 568 template<typename _Tp> \ 569 inline typename valarray<_Tp>::template _UnaryOp<_Name>::_Rt \ 570 valarray<_Tp>::operator _Op() const \ 571 { \ 572 typedef _UnClos<_Name,_ValArray,_Tp> _Closure; \ 573 typedef typename __fun<_Name, _Tp>::result_type _Rt; \ 574 return _Expr<_Closure, _Rt>(_Closure(*this)); \ 575 } 576 577 _DEFINE_VALARRAY_UNARY_OPERATOR(+, __unary_plus) 578 _DEFINE_VALARRAY_UNARY_OPERATOR(-, __negate) 579 _DEFINE_VALARRAY_UNARY_OPERATOR(~, __bitwise_not) 580 _DEFINE_VALARRAY_UNARY_OPERATOR (!, __logical_not) 581 582 #undef _DEFINE_VALARRAY_UNARY_OPERATOR 583 584 #define _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(_Op, _Name) \ 585 template<class _Tp> \ 586 inline valarray<_Tp>& \ 587 valarray<_Tp>::operator _Op##=(const _Tp &__t) \ 588 { \ 589 _Array_augmented_##_Name(_Array<_Tp>(_M_data), _M_size, __t); \ 590 return *this; \ 591 } \ 592 \ 593 template<class _Tp> \ 594 inline valarray<_Tp>& \ 595 valarray<_Tp>::operator _Op##=(const valarray<_Tp> &__v) \ 596 { \ 597 _Array_augmented_##_Name(_Array<_Tp>(_M_data), _M_size, \ 598 _Array<_Tp>(__v._M_data)); \ 599 return *this; \ 600 } 601 602 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(+, __plus) 603 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(-, __minus) 604 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(*, __multiplies) 605 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(/, __divides) 606 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(%, __modulus) 607 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(^, __bitwise_xor) 608 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(&, __bitwise_and) 609 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(|, __bitwise_or) 610 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(<<, __shift_left) 611 _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT(>>, __shift_right) 612 613 #undef _DEFINE_VALARRAY_AUGMENTED_ASSIGNMENT 614 615 #define _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(_Op, _Name) \ 616 template<class _Tp> template<class _Dom> \ 617 inline valarray<_Tp>& \ 618 valarray<_Tp>::operator _Op##=(const _Expr<_Dom,_Tp>& __e) \ 619 { \ 620 _Array_augmented_##_Name(_Array<_Tp>(_M_data), __e, _M_size); \ 621 return *this; \ 622 } 623 624 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(+, __plus) 625 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(-, __minus) 626 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(*, __multiplies) 627 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(/, __divides) 628 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(%, __modulus) 629 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(^, __bitwise_xor) 630 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(&, __bitwise_and) 631 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(|, __bitwise_or) 632 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(<<, __shift_left) 633 _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT(>>, __shift_right) 634 635 #undef _DEFINE_VALARRAY_EXPR_AUGMENTED_ASSIGNMENT 636 637 638 #define _DEFINE_BINARY_OPERATOR(_Op, _Name) \ 639 template<typename _Tp> \ 640 inline _Expr<_BinClos<_Name,_ValArray,_ValArray,_Tp,_Tp>, \ 641 typename __fun<_Name, _Tp>::result_type> \ 642 operator _Op(const valarray<_Tp>& __v, const valarray<_Tp>& __w) \ 643 { \ 644 typedef _BinClos<_Name,_ValArray,_ValArray,_Tp,_Tp> _Closure; \ 645 typedef typename __fun<_Name, _Tp>::result_type _Rt; \ 646 return _Expr<_Closure, _Rt>(_Closure(__v, __w)); \ 647 } \ 648 \ 649 template<typename _Tp> \ 650 inline _Expr<_BinClos<_Name,_ValArray,_Constant,_Tp,_Tp>, \ 651 typename __fun<_Name, _Tp>::result_type> \ 652 operator _Op(const valarray<_Tp>& __v, const _Tp& __t) \ 653 { \ 654 typedef _BinClos<_Name,_ValArray,_Constant,_Tp,_Tp> _Closure; \ 655 typedef typename __fun<_Name, _Tp>::result_type _Rt; \ 656 return _Expr<_Closure, _Rt>(_Closure(__v, __t)); \ 657 } \ 658 \ 659 template<typename _Tp> \ 660 inline _Expr<_BinClos<_Name,_Constant,_ValArray,_Tp,_Tp>, \ 661 typename __fun<_Name, _Tp>::result_type> \ 662 operator _Op(const _Tp& __t, const valarray<_Tp>& __v) \ 663 { \ 664 typedef _BinClos<_Name,_Constant,_ValArray,_Tp,_Tp> _Closure; \ 665 typedef typename __fun<_Name, _Tp>::result_type _Rt; \ 666 return _Expr<_Closure, _Tp>(_Closure(__t, __v)); \ 667 } 668 669 _DEFINE_BINARY_OPERATOR(+, __plus) 670 _DEFINE_BINARY_OPERATOR(-, __minus) 671 _DEFINE_BINARY_OPERATOR(*, __multiplies) 672 _DEFINE_BINARY_OPERATOR(/, __divides) 673 _DEFINE_BINARY_OPERATOR(%, __modulus) 674 _DEFINE_BINARY_OPERATOR(^, __bitwise_xor) 675 _DEFINE_BINARY_OPERATOR(&, __bitwise_and) 676 _DEFINE_BINARY_OPERATOR(|, __bitwise_or) 677 _DEFINE_BINARY_OPERATOR(<<, __shift_left) 678 _DEFINE_BINARY_OPERATOR(>>, __shift_right) 679 _DEFINE_BINARY_OPERATOR(&&, __logical_and) 680 _DEFINE_BINARY_OPERATOR(||, __logical_or) 681 _DEFINE_BINARY_OPERATOR(==, __equal_to) 682 _DEFINE_BINARY_OPERATOR(!=, __not_equal_to) 683 _DEFINE_BINARY_OPERATOR(<, __less) 684 _DEFINE_BINARY_OPERATOR(>, __greater) 685 _DEFINE_BINARY_OPERATOR(<=, __less_equal) 686 _DEFINE_BINARY_OPERATOR(>=, __greater_equal) 687 688 } // namespace std 689 690 #endif // _CPP_VALARRAY 691 692 // Local Variables: 693 // mode:c++ 694 // End: 695