Skip to main content
  • 2777 Accesses

Abstract

Templates are exceptionally good at forcing the compiler and optimizer to perform some work only when the executable program is generated. By definition, this is called static work. This is as opposed to dynamic work, which refers to what is done when the program runs.

This is a preview of subscription content, log in via an institution to check access.

Access this chapter

Chapter
USD 29.95
Price excludes VAT (USA)
  • Available as PDF
  • Read on any device
  • Instant download
  • Own it forever
eBook
USD 69.99
Price excludes VAT (USA)
  • Available as EPUB and PDF
  • Read on any device
  • Instant download
  • Own it forever
Softcover Book
USD 89.99
Price excludes VAT (USA)
  • Compact, lightweight edition
  • Dispatched in 3 to 5 business days
  • Free shipping worldwide - see info

Tax calculation will be finalised at checkout

Purchases are for personal use only

Institutional subscriptions

Notes

  1. 1.

    Remember that the preprocessor runs before the compiler so it cannot rely on sizeof.

  2. 2.

    Read the previous note again ☺.

  3. 3.

    See also http://www.boost.org/doc/libs/1_46_0/libs/wave/doc/preface.html .

  4. 4.

    This example was taken from a private conversation with Marco Marcello.

  5. 5.

    I do not always use the derivation notation in the book, mainly for sake of clarity. However, I strongly encourage adopting it in production code, as it boosts code reuse.

  6. 6.

    Except casts to non-integer types. For example, N*1.2 is illegal, but N+N/5 is fine.

  7. 7.

    In practice, N is always even, so N-N/2 == N/2.

  8. 8.

    See also the double-check stop in Section 7.2.

  9. 9.

    I insist that the problem is solvable because the implementations of is_integer<long> and is_integer<ptrdiff_t> are identical; otherwise, it is ill-formed. For a counterexample, consider the problem of converting a time_t and long to a string; even if time_t is long, the strings need to be different. Therefore, this issue cannot be solved by TMP techniques.

  10. 10.

    This is a good thing, because a well-built template class shouldn’t need it.

  11. 11.

    Here, FAKE and FAKE+1 both work.

  12. 12.

    Same does not imply that all functions must be identical, as some differences may have a limited impact on “uniform use”. As a trivial example, arguments may be passed by value or by const reference.

  13. 13.

    Available at: cantrip.org/trails.html. The article cites as previous bibliography [10], [11] and [12].

  14. 14.

    The sentences have been slightly rearranged.

  15. 15.

    The term type traits, introduced by John Maddock and Steve Cleary, is used here as a common name, but it is also popular as a proper name, denoting a particular library implementation. See http://cppreference.com/header/type_traits or http://www.boost.org/doc/libs/1_57_0/libs/type_traits/doc/html/index.html .

  16. 16.

    In modern C++, there’s a dedicated <type_traits> header that contains most of the metafunctions described here, and many more that cannot be replicated in classic C++. For example, has_trivial_destructor<T> is indeducible without the cooperation of the compiler, and current implementations always return false, except for built-in types.

  17. 17.

    It’s possible to define add_reference<void>::type to be void.

  18. 18.

    This is actually used. Some smart pointers, including std::unique_ptr, use operator delete [] when the type matches T[] and single deletion in any other case.

  19. 19.

    Alternatively, std::pair<const int, double> is neither const nor assignable.

  20. 20.

    The expression “type dismantling” was introduced by Stephen C. Dewhurst.

  21. 21.

    The C++ Standard contains an informative section, called “Implementation Quantities,” where a recommended minimum is suggested for the number of template arguments (1024) and for nested template instantiations (1024), but compilers do not need to respect these numbers.

  22. 22.

    The reference on the argument is [3].

  23. 23.

    The boost preprocessor library would be more suitable, anyway, but its description would require another chapter. Here, the focus is on the word simple: a strategic hand-written macro can improve the esthetics of code noticeably.

  24. 24.

    In principle, some_default should not be explicitly specified. All forms of code duplication can lead to maintenance errors. Here, I show it to emphasize the rotation.

  25. 25.

    See Section 3.6.3.

  26. 26.

    This need not be a problem’ if join_digits were a functor, clients would likely take it as X anyway.

  27. 27.

    It’s another exercise of type dismantling; note also that using push_back instead of push_front would reverse the container.

  28. 28.

    I adopted the name find_if with some abuse of notation; a genuine static_find_if would be static_find_if<typename T, template <typename X> class F>, which returns the first type in T where F<X>::value is true.

Author information

Authors and Affiliations

Authors

Rights and permissions

Reprints and permissions

Copyright information

© 2015 Davide Di Gennaro

About this chapter

Cite this chapter

Gennaro, D.D. (2015). Static Programming. In: Advanced Metaprogramming in Classic C++. Apress, Berkeley, CA. https://doi.org/10.1007/978-1-4842-1010-9_3

Download citation

Publish with us

Policies and ethics