Introduction
{fmt} is a formatting library for C++ that provides a fast, safe, and expressive alternative to printf and C++ iostreams. Its design was adopted into the C++20 standard as std::format, making it the de facto modern formatting solution for C++ projects.
What {fmt} Does
- Formats strings with a Python-like syntax using replacement fields and format specifiers
- Provides type-safe formatting that catches errors at compile time
- Supports custom formatters for user-defined types via specialization
- Handles locale-independent and locale-aware formatting of dates, times, and numbers
- Offers print functions that write directly to a file or stdout without intermediate strings
Architecture Overview
{fmt} uses a two-phase approach: format strings are parsed at compile time to validate argument types and specifiers, then formatted at runtime using optimized output routines. The library uses a type-erased argument list internally to keep binary size small while supporting an unlimited number of arguments.
Self-Hosting & Configuration
- Header-only mode available by defining FMT_HEADER_ONLY
- Integrates via CMake with find_package(fmt) or as a subdirectory
- Available through vcpkg, Conan, and most Linux package managers
- Compile-time format string checks enabled by default in C++20 mode
- Configure output locale via fmt::format with locale parameter
Key Features
- Benchmarks faster than printf and significantly faster than iostreams
- Compile-time format string validation prevents runtime errors
- Named arguments for readable format strings: fmt::format("{name}", "name"_a=value)
- Built-in support for ranges, containers, chrono types, and std::filesystem paths
- Small compiled code size compared to alternatives
Comparison with Similar Tools
- printf — printf is ubiquitous but type-unsafe; {fmt} catches mismatches at compile time
- std::format (C++20) — std::format is based on {fmt} but {fmt} offers more features and wider compiler support
- iostreams — iostreams are safe but slow and verbose; {fmt} is both faster and more concise
- Boost.Format — Boost.Format is type-safe but significantly slower than {fmt}
FAQ
Q: Is {fmt} header-only? A: It can be used header-only by defining FMT_HEADER_ONLY, but the default compiled mode produces smaller binaries and faster builds.
Q: What compilers does {fmt} support? A: GCC 4.8+, Clang 3.4+, MSVC 19.10+, and most other modern C++ compilers.
Q: How does {fmt} relate to std::format? A: The C++20 std::format specification is based on {fmt}. The library remains useful for features not yet in the standard and for projects targeting older C++ standards.
Q: Can I format custom types? A: Yes. Specialize fmt::formatter with parse and format methods to enable formatting for any type.