1 //=================================================================================================
2 /*!
3 //  \file blaze/math/Infinity.h
4 //  \brief Numerical infinity for built-in data types.
5 //
6 //  Copyright (C) 2012-2020 Klaus Iglberger - All Rights Reserved
7 //
8 //  This file is part of the Blaze library. You can redistribute it and/or modify it under
9 //  the terms of the New (Revised) BSD License. Redistribution and use in source and binary
10 //  forms, with or without modification, are permitted provided that the following conditions
11 //  are met:
12 //
13 //  1. Redistributions of source code must retain the above copyright notice, this list of
14 //     conditions and the following disclaimer.
15 //  2. Redistributions in binary form must reproduce the above copyright notice, this list
16 //     of conditions and the following disclaimer in the documentation and/or other materials
17 //     provided with the distribution.
18 //  3. Neither the names of the Blaze development group nor the names of its contributors
19 //     may be used to endorse or promote products derived from this software without specific
20 //     prior written permission.
21 //
22 //  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY
23 //  EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
24 //  OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
25 //  SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26 //  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
27 //  TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
28 //  BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 //  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30 //  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
31 //  DAMAGE.
32 */
33 //=================================================================================================
34 
35 #ifndef _BLAZE_MATH_INFINITY_H_
36 #define _BLAZE_MATH_INFINITY_H_
37 
38 
39 //*************************************************************************************************
40 // Includes
41 //*************************************************************************************************
42 
43 #include <blaze/system/Platform.h>
44 #include <blaze/util/constraints/Builtin.h>
45 #include <blaze/util/Limits.h>
46 #include <blaze/util/Types.h>
47 
48 
49 namespace blaze {
50 
51 //=================================================================================================
52 //
53 //  CLASS DEFINITION
54 //
55 //=================================================================================================
56 
57 //*************************************************************************************************
58 /*!\brief Negative infinity for built-in data types.
59 // \ingroup math
60 //
61 // The NegativeInfinity class is a wrapper class around the functionality of the blaze::Limits
62 // class to provide the possibility to assign negative infinity values to built-in data types.
63 // As negative infinity value, the largest possible negative value of the corresponding data
64 // type is used. In order to assign the negative infinity value, the NegativeInfinity class
65 // can be implicitly converted to all signed integral and floating point data types:
66 //
67 // <ul>
68 //    <li>integers</li>
69 //    <ul>
70 //       <li>signed char, char, wchar_t</li>
71 //       <li>short</li>
72 //       <li>int</li>
73 //       <li>long</li>
74 //       <li>ptrdiff_t (for certain 64-bit compilers)</li>
75 //    </ul>
76 //    <li>floating points</li>
77 //    <ul>
78 //       <li>float</li>
79 //       <li>double</li>
80 //       <li>long double</li>
81 //    </ul>
82 // </ul>
83 //
84 // \note The NegativeInfinity class is a helper class for the Infinity class. It cannot be
85 // instantiated on its own, but can only be used by the Infinity class.
86 */
87 template< typename I >  // Positive infinity type
88 class NegativeInfinity
89 {
90  public:
91    //**Type definitions****************************************************************************
92    using PositiveType = I;  //!< The positive infinity type.
93    //**********************************************************************************************
94 
95  private:
96    //**Constructors********************************************************************************
97    /*!\name Constructors */
98    //@{
99    constexpr NegativeInfinity();
100    NegativeInfinity( const NegativeInfinity& ) = default;
101    //@}
102    //**********************************************************************************************
103 
104  public:
105    //**Destructor**********************************************************************************
106    /*!\name Destructor */
107    //@{
108    ~NegativeInfinity() = default;
109    //@}
110    //**********************************************************************************************
111 
112    //**Conversion operators************************************************************************
113    /*!\name Conversion operators */
114    //@{
115    constexpr operator signed char() const;
116    constexpr operator char()        const;
117    constexpr operator wchar_t()     const;
118    constexpr operator short()       const;
119    constexpr operator int()         const;
120    constexpr operator long()        const;
121 #if BLAZE_WIN32_PLATFORM || BLAZE_WIN64_PLATFORM
122    constexpr operator ptrdiff_t()   const;
123 #endif
124    constexpr operator float()       const;
125    constexpr operator double()      const;
126    constexpr operator long double() const;
127    //@}
128    //**********************************************************************************************
129 
130    //**Utility functions***************************************************************************
131    /*!\name Utility functions */
132    //@{
133    template< typename T >
134    constexpr bool equal( const T& rhs ) const;
135    //@}
136    //**********************************************************************************************
137 
138    //**Forbidden operations************************************************************************
139    /*!\name Forbidden operations */
140    //@{
141    NegativeInfinity& operator=( const NegativeInfinity& ) = delete;
142    void* operator&() const = delete;
143    //@}
144    //**********************************************************************************************
145 
146  private:
147    //**Friend declarations*************************************************************************
148    /*! \cond BLAZE_INTERNAL */
149    friend class Infinity;
150    /*! \endcond */
151    //**********************************************************************************************
152 };
153 //*************************************************************************************************
154 
155 
156 
157 
158 //=================================================================================================
159 //
160 //  CONSTRUCTORS
161 //
162 //=================================================================================================
163 
164 //*************************************************************************************************
165 /*!\brief The default constructor of the NegativeInfinity class.
166 */
167 template< typename I >  // Positive infinity type
NegativeInfinity()168 constexpr NegativeInfinity<I>::NegativeInfinity()
169 {}
170 //*************************************************************************************************
171 
172 
173 
174 
175 //=================================================================================================
176 //
177 //  CONVERSION OPERATORS
178 //
179 //=================================================================================================
180 
181 //*************************************************************************************************
182 /*!\brief Conversion operator to the signed char built-in type.
183 //
184 // The conversion operator returns the smallest possible signed char value.
185 */
186 template< typename I >  // Positive infinity type
187 constexpr NegativeInfinity<I>::operator signed char() const
188 {
189    return Limits<signed char>::ninf();
190 }
191 //*************************************************************************************************
192 
193 
194 //*************************************************************************************************
195 /*!\brief Conversion operator to the char built-in type.
196 //
197 // The conversion operator returns the smallest possible char value.
198 */
199 template< typename I >  // Positive infinity type
200 constexpr NegativeInfinity<I>::operator char() const
201 {
202    return Limits<char>::ninf();
203 }
204 //*************************************************************************************************
205 
206 
207 //*************************************************************************************************
208 /*!\brief Conversion operator to the wchar_t built-in type.
209 //
210 // The conversion operator returns the smallest possible wchar_t value.
211 */
212 template< typename I >  // Positive infinity type
wchar_t()213 constexpr NegativeInfinity<I>::operator wchar_t() const
214 {
215    return Limits<wchar_t>::ninf();
216 }
217 //*************************************************************************************************
218 
219 
220 //*************************************************************************************************
221 /*!\brief Conversion operator to the short built-in type.
222 //
223 // The conversion operator returns the smallest possible short value.
224 */
225 template< typename I >  // Positive infinity type
226 constexpr NegativeInfinity<I>::operator short() const
227 {
228    return Limits<short>::ninf();
229 }
230 //*************************************************************************************************
231 
232 
233 //*************************************************************************************************
234 /*!\brief Conversion operator to the int built-in type.
235 //
236 // The conversion operator returns the smallest possible int value.
237 */
238 template< typename I >  // Positive infinity type
239 constexpr NegativeInfinity<I>::operator int() const
240 {
241    return Limits<int>::ninf();
242 }
243 //*************************************************************************************************
244 
245 
246 //*************************************************************************************************
247 /*!\brief Conversion operator to the long built-in type.
248 //
249 // The conversion operator returns the smallest possible long value.
250 */
251 template< typename I >  // Positive infinity type
252 constexpr NegativeInfinity<I>::operator long() const
253 {
254    return Limits<long>::ninf();
255 }
256 //*************************************************************************************************
257 
258 
259 //*************************************************************************************************
260 #if BLAZE_WIN32_PLATFORM || BLAZE_WIN64_PLATFORM
261 /*!\brief Conversion operator to the ptrdiff_t built-in type.
262 //
263 // The conversion operator returns the smallest possible ptrdiff_t value.
264 */
265 template< typename I >  // Positive infinity type
ptrdiff_t()266 constexpr NegativeInfinity<I>::operator ptrdiff_t() const
267 {
268    return Limits<ptrdiff_t>::ninf();
269 }
270 #endif
271 //*************************************************************************************************
272 
273 
274 //*************************************************************************************************
275 /*!\brief Conversion operator to the float built-in type.
276 //
277 // The conversion operator returns the smallest possible float value.
278 */
279 template< typename I >  // Positive infinity type
280 constexpr NegativeInfinity<I>::operator float() const
281 {
282    return Limits<float>::ninf();
283 }
284 //*************************************************************************************************
285 
286 
287 //*************************************************************************************************
288 /*!\brief Conversion operator to the double built-in type.
289 //
290 // The conversion operator returns the smallest possible double value.
291 */
292 template< typename I >  // Positive infinity type
293 constexpr NegativeInfinity<I>::operator double() const
294 {
295    return Limits<double>::ninf();
296 }
297 //*************************************************************************************************
298 
299 
300 //*************************************************************************************************
301 /*!\brief Conversion operator to the long double built-in type.
302 //
303 // The conversion operator returns the smallest possible long double value.
304 */
305 template< typename I >  // Positive infinity type
306 constexpr NegativeInfinity<I>::operator long double() const
307 {
308    return Limits<long double>::ninf();
309 }
310 //*************************************************************************************************
311 
312 
313 
314 
315 //=================================================================================================
316 //
317 //  UTILITY FUNCTIONS
318 //
319 //=================================================================================================
320 
321 //*************************************************************************************************
322 /*!\brief Equality comparison to a built-in data type.
323 //
324 // This function compares built-in data types with their largest possible value. The function
325 // only works for built-in data types. The attempt to compare user-defined class types will
326 // result in a compile time error.
327 */
328 template< typename I >  // Positive infinity type
329 template< typename T >  // Built-in data type
equal(const T & rhs)330 constexpr bool NegativeInfinity<I>::equal( const T& rhs ) const
331 {
332    BLAZE_CONSTRAINT_MUST_BE_BUILTIN_TYPE( T );
333    return Limits<T>::ninf() == rhs;
334 }
335 //*************************************************************************************************
336 
337 
338 
339 
340 //=================================================================================================
341 //
342 //  GLOBAL OPERATORS
343 //
344 //=================================================================================================
345 
346 //*************************************************************************************************
347 /*!\name NegativeInfinity operators */
348 //@{
349 template< typename I1, typename I2 >
350 constexpr bool operator==( const NegativeInfinity<I1>& lhs, const NegativeInfinity<I2>& rhs );
351 
352 template< typename I, typename T >
353 constexpr bool operator==( const NegativeInfinity<I>& lhs, const T& rhs );
354 
355 template< typename I, typename T >
356 constexpr bool operator==( const T& lhs, const NegativeInfinity<I>& rhs );
357 
358 template< typename I1, typename I2 >
359 constexpr bool operator!=( const NegativeInfinity<I1>& lhs, const NegativeInfinity<I2>& rhs );
360 
361 template< typename I, typename T >
362 constexpr bool operator!=( const NegativeInfinity<I>& lhs, const T& rhs );
363 
364 template< typename I, typename T >
365 constexpr bool operator!=( const T& lhs, const NegativeInfinity<I>& rhs );
366 //@}
367 //*************************************************************************************************
368 
369 
370 //*************************************************************************************************
371 /*!\brief Equality comparison between two NegativeInfinity objects.
372 // \ingroup math
373 //
374 // \return \a true.
375 */
376 template< typename I1    // Left-hand side positive infinity type
377         , typename I2 >  // Right-hand side positive infinity type
378 constexpr bool operator==( const NegativeInfinity<I1>& /*lhs*/, const NegativeInfinity<I2>& /*rhs*/ )
379 {
380    return true;
381 }
382 //*************************************************************************************************
383 
384 
385 //*************************************************************************************************
386 /*!\brief Equality comparison between an NegativeInfinity object and a built-in data type.
387 // \ingroup math
388 //
389 // \param lhs The left-hand side NegativeInfinity object.
390 // \param rhs The right-hand side built-in data value.
391 // \return \a true if the built-in data value is negative infinity, \a false if not.
392 //
393 // This operator works only for built-in data types. The attempt to compare user-defined class
394 // types will result in a compile time error.
395 */
396 template< typename I    // Positive infinity type
397         , typename T >  // Built-in data type
398 constexpr bool operator==( const NegativeInfinity<I>& lhs, const T& rhs )
399 {
400    return lhs.equal( rhs );
401 }
402 //*************************************************************************************************
403 
404 
405 //*************************************************************************************************
406 /*!\brief Equality comparison between a built-in data type and an NegativeInfinity object.
407 // \ingroup math
408 //
409 // \param lhs The left-hand side built-in data value.
410 // \param rhs The right-hand side NegativeInfinity object.
411 // \return \a true if the built-in data value is negative infinity, \a false if not.
412 //
413 // This operator works only for built-in data types. The attempt to compare user-defined class
414 // types will result in a compile time error.
415 */
416 template< typename I    // Positive infinity type
417         , typename T >  // Built-in data type
418 constexpr bool operator==( const T& lhs, const NegativeInfinity<I>& rhs )
419 {
420    return rhs.equal( lhs );
421 }
422 //*************************************************************************************************
423 
424 
425 //*************************************************************************************************
426 /*!\brief Inequality comparison between two NegativeInfinity objects.
427 // \ingroup math
428 //
429 // \return \a false.
430 */
431 template< typename I1    // Left-hand side positive infinity type
432         , typename I2 >  // Right-hand side positive infinity type
433 constexpr bool operator!=( const NegativeInfinity<I1>& /*lhs*/, const NegativeInfinity<I2>& /*rhs*/ )
434 {
435    return false;
436 }
437 //*************************************************************************************************
438 
439 
440 //*************************************************************************************************
441 /*!\brief Inequality comparison between an NegativeInfinity object and a built-in data type.
442 // \ingroup math
443 //
444 // \param lhs The left-hand side NegativeInfinity object.
445 // \param rhs The right-hand side built-in data value.
446 // \return \a true if the built-in data value is not negative infinity, \a false if it is.
447 //
448 // This operator works only for built-in data types. The attempt to compare user-defined class
449 // types will result in a compile time error.
450 */
451 template< typename I    // Positive infinity type
452         , typename T >  // Built-in data type
453 constexpr bool operator!=( const NegativeInfinity<I>& lhs, const T& rhs )
454 {
455    return !lhs.equal( rhs );
456 }
457 //*************************************************************************************************
458 
459 
460 //*************************************************************************************************
461 /*!\brief Inequality comparison between a built-in data type and an NegativeInfinity object.
462 // \ingroup math
463 //
464 // \param lhs The left-hand side built-in data value.
465 // \param rhs The right-hand side NegativeInfinity object.
466 // \return \a true if the built-in data value is not negative infinity, \a false if it is.
467 //
468 // This operator works only for built-in data types. The attempt to compare user-defined class
469 // types will result in a compile time error.
470 */
471 template< typename I    // Positive infinity type
472         , typename T >  // Built-in data type
473 constexpr bool operator!=( const T& lhs, const NegativeInfinity<I>& rhs )
474 {
475    return !rhs.equal( lhs );
476 }
477 //*************************************************************************************************
478 
479 
480 
481 
482 
483 
484 
485 
486 //=================================================================================================
487 //
488 //  CLASS DEFINITION
489 //
490 //=================================================================================================
491 
492 //*************************************************************************************************
493 /*!\brief Positive infinity for built-in data types.
494 // \ingroup math
495 //
496 // The Infinity class is a wrapper class around the functionality of the blaze::Limits class
497 // to provide the possiblity to assign a positive infinity value to built-in data types.
498 // As positive infinity value, the largest possible positive value of the corresponding
499 // data type is used. In order to assign the positive infinity value, the Infinity class
500 // can be implicitly converted to the following 13 built-in integral and floating point
501 // data types:
502 //
503 // <ul>
504 //    <li>integers</li>
505 //    <ul>
506 //       <li>unsigned char, signed char, char, wchar_t</li>
507 //       <li>unsigned short, short</li>
508 //       <li>unsigned int, int</li>
509 //       <li>unsigned long, long</li>
510 //    </ul>
511 //    <li>floating points</li>
512 //    <ul>
513 //       <li>float</li>
514 //       <li>double</li>
515 //       <li>long double</li>
516 //    </ul>
517 // </ul>
518 //
519 // In order to be able to assign infinity values, the global Infinity instance blaze::inf
520 // is provided, which can be used wherever a built-in data type is required.
521 
522    \code
523    int i    =  inf;  // Assigns a positive infinity value
524    double d = -inf;  // Assigns a negative infinity value
525    ...
526    \endcode
527 */
528 class Infinity
529 {
530  public:
531    //**Type definitions****************************************************************************
532    using NegativeType = NegativeInfinity<Infinity>;  //!< The negative infinity type.
533    //**********************************************************************************************
534 
535    //**Constructors********************************************************************************
536    /*!\name Constructors */
537    //@{
538    constexpr Infinity();
539    Infinity( const Infinity& ) = default;
540    //@}
541    //**********************************************************************************************
542 
543    //**Destructor**********************************************************************************
544    /*!\name Destructor */
545    //@{
546    ~Infinity() = default;
547    //@}
548    //**********************************************************************************************
549 
550    //**Conversion operators************************************************************************
551    /*!\name Conversion operators */
552    //@{
553    constexpr operator unsigned char()  const;
554    constexpr operator signed char()    const;
555    constexpr operator char()           const;
556    constexpr operator wchar_t()        const;
557    constexpr operator unsigned short() const;
558    constexpr operator short()          const;
559    constexpr operator unsigned int()   const;
560    constexpr operator int()            const;
561    constexpr operator unsigned long()  const;
562    constexpr operator long()           const;
563 #if BLAZE_WIN32_PLATFORM || BLAZE_WIN64_PLATFORM
564    constexpr operator size_t()         const;
565    constexpr operator ptrdiff_t()      const;
566 #endif
567    constexpr operator float()          const;
568    constexpr operator double()         const;
569    constexpr operator long double()    const;
570    //@}
571    //**********************************************************************************************
572 
573    //**Arithmetic operators************************************************************************
574    /*!\name Arithmetic operators */
575    //@{
576    constexpr const Infinity&    operator+() const;
577    constexpr const NegativeType operator-() const;
578    //@}
579    //**********************************************************************************************
580 
581    //**Utility functions***************************************************************************
582    /*!\name Utility functions */
583    //@{
584    template< typename T >
585    constexpr bool equal( const T& rhs ) const;
586    //@}
587    //**********************************************************************************************
588 
589    //**Forbidden operations************************************************************************
590    /*!\name Forbidden operations */
591    //@{
592    Infinity& operator=( const Infinity& ) = delete;
593    void* operator&() const = delete;
594    //@}
595    //**********************************************************************************************
596 };
597 //*************************************************************************************************
598 
599 
600 
601 
602 //=================================================================================================
603 //
604 //  CONSTRUCTORS
605 //
606 //=================================================================================================
607 
608 //*************************************************************************************************
609 /*!\brief The default constructor of the Infinity class.
610 */
Infinity()611 constexpr Infinity::Infinity()
612 {}
613 //*************************************************************************************************
614 
615 
616 
617 
618 //=================================================================================================
619 //
620 //  CONVERSION OPERATORS
621 //
622 //=================================================================================================
623 
624 //*************************************************************************************************
625 /*!\brief Conversion operator to the unsigned char built-in type.
626 //
627 // The conversion operator returns the largest possible unsigned char value.
628 */
629 constexpr Infinity::operator unsigned char() const
630 {
631    return Limits<unsigned char>::inf();
632 }
633 //*************************************************************************************************
634 
635 
636 //*************************************************************************************************
637 /*!\brief Conversion operator to the char built-in type.
638 //
639 // The conversion operator returns the largest possible char value.
640 */
641 constexpr Infinity::operator char() const
642 {
643    return Limits<char>::inf();
644 }
645 //*************************************************************************************************
646 
647 
648 //*************************************************************************************************
649 /*!\brief Conversion operator to the signed char built-in type.
650 //
651 // The conversion operator returns the largest possible signed char value.
652 */
653 constexpr Infinity::operator signed char() const
654 {
655    return Limits<signed char>::inf();
656 }
657 //*************************************************************************************************
658 
659 
660 //*************************************************************************************************
661 /*!\brief Conversion operator to the wchar_t built-in type.
662 //
663 // The conversion operator returns the largest possible wchar_t value.
664 */
wchar_t()665 constexpr Infinity::operator wchar_t() const
666 {
667    return Limits<wchar_t>::inf();
668 }
669 //*************************************************************************************************
670 
671 
672 //*************************************************************************************************
673 /*!\brief Conversion operator to the unsigned short built-in type.
674 //
675 // The conversion operator returns the largest possible unsigned short value.
676 */
677 constexpr Infinity::operator unsigned short() const
678 {
679    return Limits<unsigned short>::inf();
680 }
681 //*************************************************************************************************
682 
683 
684 //*************************************************************************************************
685 /*!\brief Conversion operator to the short built-in type.
686 //
687 // The conversion operator returns the largest possible short value.
688 */
689 constexpr Infinity::operator short() const
690 {
691    return Limits<short>::inf();
692 }
693 //*************************************************************************************************
694 
695 
696 //*************************************************************************************************
697 /*!\brief Conversion operator to the unsigned int built-in type.
698 //
699 // The conversion operator returns the largest possible unsigned int value.
700 */
701 constexpr Infinity::operator unsigned int() const
702 {
703    return Limits<unsigned int>::inf();
704 }
705 //*************************************************************************************************
706 
707 
708 //*************************************************************************************************
709 /*!\brief Conversion operator to the int built-in type.
710 //
711 // The conversion operator returns the largest possible int value.
712 */
713 constexpr Infinity::operator int() const
714 {
715    return Limits<int>::inf();
716 }
717 //*************************************************************************************************
718 
719 
720 //*************************************************************************************************
721 /*!\brief Conversion operator to the unsigned long built-in type.
722 //
723 // The conversion operator returns the largest possible unsigned long value.
724 */
725 constexpr Infinity::operator unsigned long() const
726 {
727    return Limits<unsigned long>::inf();
728 }
729 //*************************************************************************************************
730 
731 
732 //*************************************************************************************************
733 /*!\brief Conversion operator to the long built-in type.
734 //
735 // The conversion operator returns the largest possible long value.
736 */
737 constexpr Infinity::operator long() const
738 {
739    return Limits<long>::inf();
740 }
741 //*************************************************************************************************
742 
743 
744 //*************************************************************************************************
745 #if BLAZE_WIN32_PLATFORM || BLAZE_WIN64_PLATFORM
746 /*!\brief Conversion operator to the size_t built-in type.
747 //
748 // The conversion operator returns the largest possible size_t value.
749 */
size_t()750 constexpr Infinity::operator size_t() const
751 {
752    return Limits<size_t>::inf();
753 }
754 #endif
755 //*************************************************************************************************
756 
757 
758 //*************************************************************************************************
759 #if BLAZE_WIN32_PLATFORM || BLAZE_WIN64_PLATFORM
760 /*!\brief Conversion operator to the ptrdiff_t built-in type.
761 //
762 // The conversion operator returns the largest possible ptrdiff_t value.
763 */
ptrdiff_t()764 constexpr Infinity::operator ptrdiff_t() const
765 {
766    return Limits<ptrdiff_t>::inf();
767 }
768 #endif
769 //*************************************************************************************************
770 
771 
772 //*************************************************************************************************
773 /*!\brief Conversion operator to the float built-in type.
774 //
775 // The conversion operator returns the largest possible float value.
776 */
777 constexpr Infinity::operator float() const
778 {
779    return Limits<float>::inf();
780 }
781 //*************************************************************************************************
782 
783 
784 //*************************************************************************************************
785 /*!\brief Conversion operator to the double built-in type.
786 //
787 // The conversion operator returns the largest possible double value.
788 */
789 constexpr Infinity::operator double() const
790 {
791    return Limits<double>::inf();
792 }
793 //*************************************************************************************************
794 
795 
796 //*************************************************************************************************
797 /*!\brief Conversion operator to the long double built-in type.
798 //
799 // The conversion operator returns the largest possible long double value.
800 */
801 constexpr Infinity::operator long double() const
802 {
803    return Limits<long double>::inf();
804 }
805 //*************************************************************************************************
806 
807 
808 
809 
810 //=================================================================================================
811 //
812 //  ARITHMETIC OPERATORS
813 //
814 //=================================================================================================
815 
816 //*************************************************************************************************
817 /*!\brief Returns the positive infinity value for all built-in data types.
818 //
819 // \return The positive infinity value.
820 */
821 constexpr const Infinity& Infinity::operator+() const
822 {
823    return *this;
824 }
825 //*************************************************************************************************
826 
827 
828 //*************************************************************************************************
829 /*!\brief Returns the negative infinity value for all built-in data types.
830 //
831 // \return The negative infinity value.
832 */
833 constexpr const Infinity::NegativeType Infinity::operator-() const
834 {
835    return NegativeType();
836 }
837 //*************************************************************************************************
838 
839 
840 
841 
842 //=================================================================================================
843 //
844 //  UTILITY FUNCTIONS
845 //
846 //=================================================================================================
847 
848 //*************************************************************************************************
849 /*!\brief Equality comparison to a built-in data type.
850 //
851 // This function compares built-in data types with their largest possible value. The function
852 // only works for built-in data types. The attempt to compare user-defined class types will
853 // result in a compile time error.
854 */
855 template< typename T >
equal(const T & rhs)856 constexpr bool Infinity::equal( const T& rhs ) const
857 {
858    BLAZE_CONSTRAINT_MUST_BE_BUILTIN_TYPE( T );
859    return Limits<T>::inf() == rhs;
860 }
861 //*************************************************************************************************
862 
863 
864 
865 
866 //=================================================================================================
867 //
868 //  GLOBAL OPERATORS
869 //
870 //=================================================================================================
871 
872 //*************************************************************************************************
873 /*!\name Infinity operators */
874 //@{
875 constexpr bool operator==( const Infinity& lhs, const Infinity& rhs );
876 
877 template< typename I >
878 constexpr bool operator==( const Infinity& lhs, const NegativeInfinity<I>& rhs );
879 
880 template< typename I >
881 constexpr bool operator==( const NegativeInfinity<I>& lhs, const Infinity& rhs );
882 
883 template< typename T >
884 constexpr bool operator==( const Infinity& lhs, const T& rhs );
885 
886 template< typename T >
887 constexpr bool operator==( const T& lhs, const Infinity& rhs );
888 
889 constexpr bool operator!=( const Infinity& lhs, const Infinity& rhs );
890 
891 template< typename I >
892 constexpr bool operator!=( const Infinity& lhs, const NegativeInfinity<I>& rhs );
893 
894 template< typename I >
895 constexpr bool operator!=( const NegativeInfinity<I>& lhs, const Infinity& rhs );
896 
897 template< typename T >
898 constexpr bool operator!=( const Infinity& lhs, const T& rhs );
899 
900 template< typename T >
901 constexpr bool operator!=( const T& lhs, const Infinity& rhs );
902 //@}
903 //*************************************************************************************************
904 
905 
906 //*************************************************************************************************
907 /*!\brief Equality comparison between two Infinity objects.
908 // \ingroup math
909 //
910 // \return \a true.
911 */
912 constexpr bool operator==( const Infinity& /*lhs*/, const Infinity& /*rhs*/ )
913 {
914    return true;
915 }
916 //*************************************************************************************************
917 
918 
919 //*************************************************************************************************
920 /*!\brief Equality comparison between an Infinity object and a NegativeInfinity object.
921 // \ingroup math
922 //
923 // \return \a false.
924 */
925 template< typename I >  // Positive infinity type
926 constexpr bool operator==( const Infinity& /*lhs*/, const NegativeInfinity<I>& /*rhs*/ )
927 {
928    return false;
929 }
930 //*************************************************************************************************
931 
932 
933 //*************************************************************************************************
934 /*!\brief Equality comparison between a NegativeInfinity object and an Infinity object.
935 // \ingroup math
936 //
937 // \return \a false.
938 */
939 template< typename I >  // Positive infinity type
940 constexpr bool operator==( const NegativeInfinity<I>& /*lhs*/, const Infinity& /*rhs*/ )
941 {
942    return false;
943 }
944 //*************************************************************************************************
945 
946 
947 //*************************************************************************************************
948 /*!\brief Equality comparison between an Infinity object and a built-in data type.
949 // \ingroup math
950 //
951 // \param lhs The left-hand side Infinity object.
952 // \param rhs The right-hand side built-in data value.
953 // \return \a true if the built-in data value is infinity, \a false if not.
954 //
955 // This operator works only for built-in data types. The attempt to compare user-defined class
956 // types will result in a compile time error.
957 */
958 template< typename T >
959 constexpr bool operator==( const Infinity& lhs, const T& rhs )
960 {
961    return lhs.equal( rhs );
962 }
963 //*************************************************************************************************
964 
965 
966 //*************************************************************************************************
967 /*!\brief Equality comparison between a built-in data type and an Infinity object.
968 // \ingroup math
969 //
970 // \param lhs The left-hand side built-in data value.
971 // \param rhs The right-hand side Infinity object.
972 // \return \a true if the built-in data value is infinity, \a false if not.
973 //
974 // This operator works only for built-in data types. The attempt to compare user-defined class
975 // types will result in a compile time error.
976 */
977 template< typename T >
978 constexpr bool operator==( const T& lhs, const Infinity& rhs )
979 {
980    return rhs.equal( lhs );
981 }
982 //*************************************************************************************************
983 
984 
985 //*************************************************************************************************
986 /*!\brief Inequality comparison between two Infinity objects.
987 // \ingroup math
988 //
989 // \return \a false.
990 */
991 constexpr bool operator!=( const Infinity& /*lhs*/, const Infinity& /*rhs*/ )
992 {
993    return false;
994 }
995 //*************************************************************************************************
996 
997 
998 //*************************************************************************************************
999 /*!\brief Inequality comparison between an Infinity object and a NegativeInfinity object.
1000 // \ingroup math
1001 //
1002 // \return \a true.
1003 */
1004 template< typename I >  // Positive infinity type
1005 constexpr bool operator!=( const Infinity& /*lhs*/, const NegativeInfinity<I>& /*rhs*/ )
1006 {
1007    return true;
1008 }
1009 //*************************************************************************************************
1010 
1011 
1012 //*************************************************************************************************
1013 /*!\brief Inequality comparison between a NegativeInfinity object and an Infinity object.
1014 // \ingroup math
1015 //
1016 // \return \a true.
1017 */
1018 template< typename I >  // Positive infinity type
1019 constexpr bool operator!=( const NegativeInfinity<I>& /*lhs*/, const Infinity& /*rhs*/ )
1020 {
1021    return true;
1022 }
1023 //*************************************************************************************************
1024 
1025 
1026 //*************************************************************************************************
1027 /*!\brief Inequality comparison between an Infinity object and a built-in data type.
1028 // \ingroup math
1029 //
1030 // \param lhs The left-hand side Infinity object.
1031 // \param rhs The right-hand side built-in data value.
1032 // \return \a true if the built-in data value is not infinity, \a false if it is.
1033 //
1034 // This operator works only for built-in data types. The attempt to compare user-defined class
1035 // types will result in a compile time error.
1036 */
1037 template< typename T >
1038 constexpr bool operator!=( const Infinity& lhs, const T& rhs )
1039 {
1040    return !lhs.equal( rhs );
1041 }
1042 //*************************************************************************************************
1043 
1044 
1045 //*************************************************************************************************
1046 /*!\brief Inequality comparison between a built-in data type and an Infinity object.
1047 // \ingroup math
1048 //
1049 // \param lhs The left-hand side built-in data value.
1050 // \param rhs The right-hand side Infinity object.
1051 // \return \a true if the built-in data value is not infinity, \a false if it is.
1052 //
1053 // This operator works only for built-in data types. The attempt to compare user-defined class
1054 // types will result in a compile time error.
1055 */
1056 template< typename T >
1057 constexpr bool operator!=( const T& lhs, const Infinity& rhs )
1058 {
1059    return !rhs.equal( lhs );
1060 }
1061 //*************************************************************************************************
1062 
1063 
1064 
1065 
1066 //=================================================================================================
1067 //
1068 //  GLOBAL INFINITY VALUE
1069 //
1070 //=================================================================================================
1071 
1072 //*************************************************************************************************
1073 /*!\brief Global Infinity instance.
1074 // \ingroup math
1075 //
1076 // The blaze::inf instance can be used wherever a built-in data type is expected. It is implicitly
1077 // converted to the corresponding built-in data type and represents its largest possible data
1078 // value.
1079 */
1080 constexpr Infinity inf;
1081 //*************************************************************************************************
1082 
1083 } // namespace blaze
1084 
1085 #endif
1086