2015-02-23 25 views
5

Yani uint32_t uint64_t için kendi politikasına sahipNumeric_cast politikasını nasıl kullanırım?

struct MyOverflowHandlerPolicy 
{ 
    void operator() (boost::numeric::range_check_result) { 
     std::cout << "MyOverflowHandlerPolicy called" << std::endl; 
     throw boost::numeric::positive_overflow(); 
    }; 
} ; 

Nasıl bu boost :: numeric_cast tarafından kullanılacak alabilirim sayısal döküm?

cevap

6

Her tür dönüştürmede numeric_cast, numeric_cast_traits uzmanlıklarını tanımlamak için özelleştirme tanımlanmalıdır. Bu uzmanlıklar, yerleşik sayısal türler için varsayılan değerlerle zaten tanımlanmıştır. BOOST_NUMERIC_CONVERSION_RELAX_BUILT_IN_CAST_TRAITS (details) tanımlanarak yerleşik türler için uzmanlık neslinin üretimini devre dışı bırakmak mümkündür.

Burada küçük bir çalışan örnek var.

#include <iostream> 
#include <stdexcept> 

#define BOOST_NUMERIC_CONVERSION_RELAX_BUILT_IN_CAST_TRAITS 
#include <boost/numeric/conversion/cast.hpp> 

using namespace std; 

struct YourOverflowHandlerPolicy 
{ 
    void operator() (boost::numeric::range_check_result r) { 
     cout << "YourOverflowHandlerPolicy called" << endl; 
     if (r != boost::numeric::cInRange) { 
      throw logic_error("Not in range!"); 
     } 
    }; 
}; 

namespace boost { namespace numeric { 
template <> 
struct numeric_cast_traits<uint32_t, uint64_t> 
{ 
    typedef YourOverflowHandlerPolicy overflow_policy; 
    typedef UseInternalRangeChecker range_checking_policy; 
    typedef Trunc<uint64_t>   rounding_policy; 
}; 

template <> 
struct numeric_cast_traits<uint64_t, uint32_t> 
{ 
    typedef YourOverflowHandlerPolicy overflow_policy; 
    typedef UseInternalRangeChecker range_checking_policy; 
    typedef Trunc<uint32_t>   rounding_policy; 
}; 
}} //namespace boost::numeric; 

int main() 
{ 
    try { 
     cout << boost::numeric_cast<uint32_t>((uint64_t)1) << endl; // OK 
     cout << boost::numeric_cast<uint32_t>((uint64_t)1<<31) << endl; // OK 
     cout << boost::numeric_cast<uint32_t>((uint64_t)1<<32) << endl; // Exception 
    } catch (...) { 
     cout << "exception" << endl; 
    } 

    return 0; 
} 

Çıktı:

YourOverflowHandlerPolicy called 
1 
YourOverflowHandlerPolicy called 
2147483648 
YourOverflowHandlerPolicy called 
exception 

Not: Ben boost salınımını 1.55.0 var, minimum yayın düzeyi derleme yapabilmek için ancak 1.46.0 ile derlenmiş değildir bilmiyorum. Yani, lütfen destek sürümünüzü kontrol edin ve gerekirse güncelleyin.