#pragma once #ifndef print_h_ #define print_h_ #ifdef HAVE_CXX11_HEADERS template struct binwrap { T data; }; template static FORCE_INLINE constexpr binwrap bin(T x) { return binwrap{x}; } template struct octwrap { T data; }; template static FORCE_INLINE constexpr octwrap oct(T x) { return octwrap{x}; } template struct hexwrap { T data; }; template static FORCE_INLINE constexpr hexwrap hex(T x) { return hexwrap{x}; } template struct HEXwrap { T data; }; template static FORCE_INLINE constexpr HEXwrap HEX(T x) { return HEXwrap{x}; } FORCE_INLINE constexpr size_t buildprintpiece(void) { return 0; } template enable_if_t::value, size_t> buildprintpiece(T x) { // log_10(2^x) = x * log(2)/log(10) ~= x * 0.30103 size_t constexpr numdigits = (sizeof(T) * CHAR_BIT + 1) / 3; char str[numdigits + 2]; // +2 for '-', '\0' char * strptr = str; size_t totalChars; if (x < 0) { size_t numChars = logbasenegative<10>(x); totalChars = numChars+1; *strptr++ = '-'; strptr[numChars] = '\0'; do { DivResult const qr = divrhs<10>(x); x = qr.q; strptr[numChars-1] = '0' - (char)qr.r; } while (--numChars); } else { size_t numChars = logbase<10>(x); totalChars = numChars; strptr[numChars] = '\0'; do { DivResult const qr = divrhs<10>(x); x = qr.q; strptr[numChars-1] = '0' + (char)qr.r; } while (--numChars); } initputs(str); return totalChars; } template enable_if_t::value, size_t> buildprintpiece(binwrap x) { make_unsigned_t const data = x.data; int constexpr numChars = sizeof(x)*CHAR_BIT; char str[numChars+1]; str[numChars] = '\0'; for (int p = 0; p < numChars; ++p) str[numChars - 1 - p] = '0' + (char)((data >> p) & 1); initputs(str); return numChars; } template enable_if_t::value, size_t> buildprintpiece(octwrap x) { make_unsigned_t const data = x.data; int constexpr numChars = (sizeof(x)*CHAR_BIT + 2) / 3; char str[numChars+1]; str[numChars] = '\0'; for (int p = 0; p < numChars; ++p) str[numChars - 1 - p] = '0' + (char)((data >> (p*3)) & 7); initputs(str); return numChars; } template enable_if_t::value, size_t> buildprintpiece(hexwrap x) { static char const hexletters[] = "0123456789abcdef"; make_unsigned_t const data = x.data; int constexpr numChars = (sizeof(x)*CHAR_BIT + 3) >> 2; char str[numChars+1]; str[numChars] = '\0'; for (int p = 0; p < numChars; ++p) str[numChars - 1 - p] = hexletters[(int)((data >> (p<<2)) & 0xF)]; initputs(str); return numChars; } template enable_if_t::value, size_t> buildprintpiece(HEXwrap x) { static char const HEXletters[] = "0123456789ABCDEF"; make_unsigned_t const data = x.data; int constexpr numChars = (sizeof(x)*CHAR_BIT + 3) >> 2; char str[numChars+1]; str[numChars] = '\0'; for (int p = 0; p < numChars; ++p) str[numChars - 1 - p] = HEXletters[(int)((data >> (p<<2)) & 0xF)]; initputs(str); return numChars; } template FORCE_INLINE size_t buildprintpiece(const T * x) { return buildprintpiece(hex((uintptr_t)x)); } FORCE_INLINE size_t buildprintpiece(char const *str) { initputs(str); return strlen(str); } template static FORCE_INLINE size_t buildprint(T first) { return buildprintpiece(first); } template size_t buildprint(T first, Args... args) { size_t const len = buildprintpiece(first); return len + buildprint(args...); } // this file is incomplete. a fuller implementation exists but has not been completed and debugged. #endif #endif // print_h_