c++ - Alternative to reinterpret_cast with constexpr functions -


below, find constexpr string literal crc32 computation.

i had reinterpret string literal character char unsigned char. because reinterpret_cast not available in constexpr function, workaround small utility function two's complement manually little disappointed it.

does exist more elegant solution deal kind of manipulation ?

#include <iostream>  class crc32gen {     uint32_t m_[256] {};      static constexpr unsigned char reinterpret_cast_schar_to_uchar( char v ) {         return v>=0 ? v : ~(v-1);     } public:     // algorithm http://create.stephan-brumme.com/crc32/#sarwate     constexpr crc32gen() {         constexpr uint32_t polynomial = 0xedb88320;         (unsigned int = 0; <= 0xff; i++) {              uint32_t crc = i;              (unsigned int j = 0; j < 8; j++)                  crc = (crc >> 1) ^ (-int(crc & 1) & polynomial);             m_[i] = crc;         }     }      constexpr uint32_t operator()( const char* data ) const {          uint32_t crc = ~0;          while (auto c = reinterpret_cast_schar_to_uchar(*data++))             crc = (crc >> 8) ^ m_[(crc & 0xff) ^ c];         return ~crc;      }  }; constexpr crc32gen const crc32gen_;  int main() {     constexpr auto const val = crc32gen_( "the character code É greater 127" );     std::cout << std::hex << val << std::endl; } 

edit : in case, static_cast<unsigned char>(*data++) enough.

two's complement not guaranteed standard; in clause 3.9.1:

7 - [...] representations of integral types shall define values use of pure binary numeration system. [example: international standard permits 2's complement, 1's complement , signed magnitude representations integral types. — end example ]

so code assumes two's complement going have perform appropriate manipulations manually.

that said, conversion function unnecessary (and possibly incorrect); signed-to-unsigned conversions can use standard integral conversion (4.7):

2 - if destination type unsigned, resulting value least unsigned integer congruent source integer (modulo 2n n number of bits used represent unsigned type). [ note: in two's complement representation, conversion conceptual , there no change in bit pattern (if there no truncation). — end note ]

corrected code, using static_cast::

constexpr uint32_t operator()( const char* data ) const {      uint32_t crc = ~0;      while (auto c = static_cast<unsigned char>(*data++))         crc = (crc >> 8) ^ m_[(crc & 0xff) ^ c];     return ~crc;  }  

Comments

Popular posts from this blog

php - regexp cyrillic filename not matches -

c# - OpenXML hanging while writing elements -

sql - Select Query has unexpected multiple records (MS Access) -