template <typename Context, typename... T, size_t NUM_ARGS, size_t NUM_NAMED_ARGS, unsigned long long DESC>
+
diff --git a/dev/search/search_index.json b/dev/search/search_index.json
index 6eb8ec08..100df7b6 100644
--- a/dev/search/search_index.json
+++ b/dev/search/search_index.json
@@ -1 +1 @@
-{"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"]},"docs":[{"location":"","title":"A modern formatting library","text":"Safety
Inspired by Python's formatting facility, {fmt} provides a safe replacement for the printf
family of functions. Errors in format strings, which are a common source of vulnerabilities in C, are reported at compile time. For example:
fmt::format(\"{:d}\", \"I am not a number\");
will give a compile-time error because
d
is not a valid format specifier for strings. APIs like
fmt::format
prevent buffer overflow errors via automatic memory management. \u2192 Learn more Extensibility
Formatting of most standard types, including all containers, dates, and times is supported out-of-the-box. For example:
fmt::print(\"{}\", std::vector{1, 2, 3});
prints the vector in a JSON-like format:
[1, 2, 3]
You can make your own types formattable and even make compile-time checks work for them. \u2192 Learn more Performance
{fmt} can be anywhere from tens of percent to 20-30 times faster than iostreams and sprintf
, especially for numeric formatting. The library minimizes dynamic memory allocations and can optionally compile format strings to optimal code.
Unicode support
{fmt} provides portable Unicode support on major operating systems with UTF-8 and char
strings. For example:
fmt::print(\"\u0421\u043b\u0430\u0432\u0430 \u0423\u043a\u0440\u0430\u0457\u043d\u0456!\");
will be printed correctly on Linux, macOS, and even Windows console, irrespective of the codepages.
The default is locale-independent, but you can opt into localized formatting and {fmt} makes it work with Unicode, addressing issues in the standard libary.
Fast compilation
The library makes extensive use of type erasure to achieve fast compilation. fmt/base.h
provides a subset of the API with minimal include dependencies and enough functionality to replace all uses of *printf
.
Code using {fmt} is usually several times faster to compile than the equivalent iostreams code, and while printf
compiles faster still, the gap is narrowing.
\u2192 Learn more Small binary footprint
Type erasure is also used to prevent template bloat, resulting in compact per-call binary code. For example, a call to fmt::print
with a single argument is just a few instructions, comparable to printf
despite adding runtime safety, and much smaller than the equivalent iostreams code.
The library itself has small binary footprint and some components such as floating-point formatting can be disabled to make it even smaller for resource-constrained devices.
Portability
{fmt} has a small self-contained codebase with the core consisting of just three headers and no external dependencies.
The library is highly portable and requires only a minimal subset of C++11 features which are available in GCC 4.9, Clang 3.4, MSVC 19.0 (2015) and later. Newer compiler and standard library features are used if available, and enable additional functionality.
Where possible, the output of formatting functions is consistent across platforms.
Open source
{fmt} is in the top hundred open-source C++ libraries on GitHub and has hundreds of all-time contributors.
The library is distributed under a permissive MIT license and is relied upon by many open-source projects, including Blender, PyTorch, Apple's FoundationDB, Windows Terminal, MongoDB, and others.
"},{"location":"api/","title":"API Reference","text":"
The {fmt} library API consists of the following components:
fmt/base.h
: the base API providing main formatting functions for char
/UTF-8 with C++20 compile-time checks and minimal dependencies fmt/format.h
: fmt::format
and other formatting functions as well as locale support fmt/ranges.h
: formatting of ranges and tuples fmt/chrono.h
: date and time formatting fmt/std.h
: formatters for standard library types fmt/compile.h
: format string compilation fmt/color.h
: terminal colors and text styles fmt/os.h
: system APIs fmt/ostream.h
: std::ostream
support fmt/args.h
: dynamic argument lists fmt/printf.h
: safe printf
fmt/xchar.h
: optional wchar_t
support
All functions and types provided by the library reside in namespace fmt
and macros have prefix FMT_
.
"},{"location":"api/#base-api","title":"Base API","text":"
fmt/base.h
defines the base API which provides main formatting functions for char
/UTF-8 with C++20 compile-time checks. It has minimal include dependencies for better compile times. This header is only beneficial when using {fmt} as a library (the default) and not in the header-only mode. It also provides formatter
specializations for the following types:
int
, long long
, unsigned
, unsigned long long
float
, double
, long double
bool
char
const char*
, fmt::string_view
const void*
The following functions use format string syntax similar to that of str.format in Python. They take fmt and args as arguments.
fmt is a format string that contains literal text and replacement fields surrounded by braces {}
. The fields are replaced with formatted arguments in the resulting string. fmt::format_string
is a format string which can be implicitly constructed from a string literal or a constexpr
string and is checked at compile time in C++20. To pass a runtime format string wrap it in fmt::runtime
.
args is an argument list representing objects to be formatted.
I/O errors are reported as std::system_error
exceptions unless specified otherwise.
template <typename...\u00a0T>\nvoid print(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to stdout
.
Example:
fmt::print(\"The answer is {}.\", 42);\n
template <typename...\u00a0T>\nvoid print(FILE* f, format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file f
.
Example:
fmt::print(stderr, \"Don't {}!\", \"panic\");\n
template <typename...\u00a0T>\nvoid println(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to stdout
followed by a newline.
template <typename...\u00a0T>\nvoid println(FILE* f, format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file f
followed by a newline.
template <typename OutputIt, typename...\u00a0T>\nauto format_to(OutputIt&& out, format_string<T...> fmt, T&&... args) -\u2060>\u00a0remove_cvref_t<OutputIt>;
Formats args
according to specifications in fmt
, writes the result to the output iterator out
and returns the iterator past the end of the output range. format_to
does not append a terminating null character.
Example:
auto out = std::vector<char>();\nfmt::format_to(std::back_inserter(out), \"{}\", 42);\n
template <typename OutputIt, typename...\u00a0T>\nauto format_to_n(OutputIt out, size_t n, format_string<T...> fmt, T&&... args) -\u2060>\u00a0format_to_n_result<OutputIt>;
Formats args
according to specifications in fmt
, writes up to n
characters of the result to the output iterator out
and returns the total (not truncated) output size and the iterator past the end of the output range. format_to_n
does not append a terminating null character.
template <typename OutputIt>\nstruct format_to_n_result;
OutputIt out;
Iterator past the end of the output range.
size_t size;
Total (not truncated) output size.
template <typename...\u00a0T>\nauto formatted_size(format_string<T...> fmt, T&&... args) -\u2060>\u00a0size_t;
Returns the number of chars in the output of format(fmt, args...)
.
"},{"location":"api/#formatting-user-defined-types","title":"Formatting User-Defined Types","text":"
The {fmt} library provides formatters for many standard C++ types. See fmt/ranges.h
for ranges and tuples including standard containers such as std::vector
, fmt/chrono.h
for date and time formatting and fmt/std.h
for other standard library types.
There are two ways to make a user-defined type formattable: providing a format_as
function or specializing the formatter
struct template.
Use format_as
if you want to make your type formattable as some other type with the same format specifiers. The format_as
function should take an object of your type and return an object of a formattable type. It should be defined in the same namespace as your type.
Example (run):
#include <fmt/format.h>\n\nnamespace kevin_namespacy {\n\nenum class film {\n house_of_cards, american_beauty, se7en = 7\n};\n\nauto format_as(film f) { return fmt::underlying(f); }\n\n}\n\nint main() {\n fmt::print(\"{}\\n\", kevin_namespacy::film::se7en); // Output: 7\n}
Using specialization is more complex but gives you full control over parsing and formatting. To use this method specialize the formatter
struct template for your type and implement parse
and format
methods.
The recommended way of defining a formatter is by reusing an existing one via inheritance or composition. This way you can support standard format specifiers without implementing them yourself. For example:
// color.h:\n#include <fmt/base.h>\n\nenum class color {red, green, blue};\n\ntemplate <> struct fmt::formatter<color>: formatter<string_view> {\n // parse is inherited from formatter<string_view>.\n\n auto format(color c, format_context& ctx) const\n -> format_context::iterator;\n};\n
// color.cc:\n#include \"color.h\"\n#include <fmt/format.h>\n\nauto fmt::formatter<color>::format(color c, format_context& ctx) const\n -> format_context::iterator {\n string_view name = \"unknown\";\n switch (c) {\n case color::red: name = \"red\"; break;\n case color::green: name = \"green\"; break;\n case color::blue: name = \"blue\"; break;\n }\n return formatter<string_view>::format(name, ctx);\n}\n
Note that formatter<string_view>::format
is defined in fmt/format.h
so it has to be included in the source file. Since parse
is inherited from formatter<string_view>
it will recognize all string format specifications, for example
fmt::format(\"{:>10}\", color::blue)\n
will return \" blue\"
.
In general the formatter has the following form:
template <> struct fmt::formatter<T> {\n // Parses format specifiers and stores them in the formatter.\n //\n // [ctx.begin(), ctx.end()) is a, possibly empty, character range that\n // contains a part of the format string starting from the format\n // specifications to be parsed, e.g. in\n //\n // fmt::format(\"{:f} continued\", ...);\n //\n // the range will contain \"f} continued\". The formatter should parse\n // specifiers until '}' or the end of the range. In this example the\n // formatter should parse the 'f' specifier and return an iterator\n // pointing to '}'.\n constexpr auto parse(format_parse_context& ctx)\n -> format_parse_context::iterator;\n\n // Formats value using the parsed format specification stored in this\n // formatter and writes the output to ctx.out().\n auto format(const T& value, format_context& ctx) const\n -> format_context::iterator;\n};
It is recommended to at least support fill, align and width that apply to the whole object and have the same semantics as in standard formatters.
You can also write a formatter for a hierarchy of classes:
// demo.h:\n#include <type_traits>\n#include <fmt/core.h>\n\nstruct A {\n virtual ~A() {}\n virtual std::string name() const { return \"A\"; }\n};\n\nstruct B : A {\n virtual std::string name() const { return \"B\"; }\n};\n\ntemplate <typename T>\nstruct fmt::formatter<T, std::enable_if_t<std::is_base_of_v<A, T>, char>> :\n fmt::formatter<std::string> {\n auto format(const A& a, format_context& ctx) const {\n return formatter<std::string>::format(a.name(), ctx);\n }\n};\n
// demo.cc:\n#include \"demo.h\"\n#include <fmt/format.h>\n\nint main() {\n B b;\n A& a = b;\n fmt::print(\"{}\", a); // Output: B\n}\n
Providing both a formatter
specialization and a format_as
overload is disallowed.
template <typename Char>\nusing basic_format_parse_context = parse_context<Char>;
class context;
context(iterator out, format_args args, detail::locale_ref loc);
Constructs a context
object. References to the arguments are stored in the object so make sure they have appropriate lifetimes.
using format_context = context;
"},{"location":"api/#compile-time-checks","title":"Compile-Time Checks","text":"
Compile-time format string checks are enabled by default on compilers that support C++20 consteval
. On older compilers you can use the FMT_STRING macro defined in fmt/format.h
instead.
Unused arguments are allowed as in Python's str.format
and ordinary functions.
template <typename Char, typename...\u00a0T>\nusing basic_format_string = basic_fstring<Char, T...>;
template <typename...\u00a0T>\nusing format_string = typename fstring<T...>::t;
auto runtime(string_view s) -\u2060>\u00a0runtime_format_string<>;
Creates a runtime format string.
Example:
// Check format string at runtime instead of compile-time.\nfmt::print(fmt::runtime(\"{:d}\"), \"I am not a number\");\n
"},{"location":"api/#named-arguments","title":"Named Arguments","text":"
template <typename Char, typename T>\nauto arg(const Char* name, const T& arg) -\u2060>\u00a0detail::named_arg<Char, T>;
Returns a named argument to be used in a formatting function. It should only be used in a call to a formatting function.
Example:
fmt::print(\"The answer is {answer}.\", fmt::arg(\"answer\", 42));\n
Named arguments are not supported in compile-time checks at the moment.
"},{"location":"api/#type-erasure","title":"Type Erasure","text":"
You can create your own formatting function with compile-time checks and small binary footprint, for example (run):
#include <fmt/format.h>\n\nvoid vlog(const char* file, int line,\n fmt::string_view fmt, fmt::format_args args) {\n fmt::print(\"{}: {}: {}\", file, line, fmt::vformat(fmt, args));\n}\n\ntemplate <typename... T>\nvoid log(const char* file, int line,\n fmt::format_string<T...> fmt, T&&... args) {\n vlog(file, line, fmt, fmt::make_format_args(args...));\n}\n\n#define MY_LOG(fmt, ...) log(__FILE__, __LINE__, fmt, __VA_ARGS__)\n\nMY_LOG(\"invalid squishiness: {}\", 42);\n
Note that vlog
is not parameterized on argument types which improves compile times and reduces binary code size compared to a fully parameterized version.
template <typename Context, typename...\u00a0T, size_t\u00a0NUM_ARGS, size_t\u00a0NUM_NAMED_ARGS, unsigned long long\u00a0DESC>\nconstexpr auto make_format_args(T&... args) -\u2060>\u00a0detail::format_arg_store<Context, NUM_ARGS, NUM_NAMED_ARGS, DESC>;
Constructs an object that stores references to arguments and can be implicitly converted to format_args
. Context
can be omitted in which case it defaults to context
. See arg
for lifetime considerations.
template <typename Context>\nclass basic_format_args;
A view of a collection of formatting arguments. To avoid lifetime issues it should only be used as a parameter type in type-erased functions such as vformat
:
void vlog(fmt::string_view fmt, fmt::format_args args); // OK\nfmt::format_args args = fmt::make_format_args(); // Dangling reference\n
constexpr basic_format_args(const store<NUM_ARGS, NUM_NAMED_ARGS, DESC>& s);
Constructs a basic_format_args
object from format_arg_store
.
constexpr basic_format_args(const format_arg* args, int count, bool has_named);
Constructs a basic_format_args
object from a dynamic list of arguments.
auto get(int id) -\u2060>\u00a0format_arg;
Returns the argument with the specified id.
using format_args = basic_format_args<context>;
template <typename Context>\nclass basic_format_arg;
auto visit(Visitor&& vis) -\u2060>\u00a0decltype(vis(0));
Visits an argument dispatching to the appropriate visit method based on the argument type. For example, if the argument type is double
then vis(value)
will be called with the value of type double
.
"},{"location":"api/#compatibility","title":"Compatibility","text":"
template <typename Char>\nclass basic_string_view;
An implementation of std::basic_string_view
for pre-C++17. It provides a subset of the API. fmt::basic_string_view
is used for format strings even if std::basic_string_view
is available to prevent issues when a library is compiled with a different -std
option than the client code (which is not recommended).
constexpr basic_string_view(const Char* s, size_t count);
Constructs a string reference object from a C string and a size.
basic_string_view(const Char* s);
Constructs a string reference object from a C string.
basic_string_view(const S& s);
Constructs a string reference from a std::basic_string
or a std::basic_string_view
object.
constexpr auto data() -\u2060>\u00a0const Char*;
Returns a pointer to the string data.
constexpr auto size() -\u2060>\u00a0size_t;
Returns the string size.
using string_view = basic_string_view<char>;
"},{"location":"api/#format-api","title":"Format API","text":"
fmt/format.h
defines the full format API providing additional formatting functions and locale support.
template <typename...\u00a0T>\nauto format(format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::string;
Formats args
according to specifications in fmt
and returns the result as a string.
Example:
#include <fmt/format.h>\nstd::string message = fmt::format(\"The answer is {}.\", 42);\n
auto vformat(string_view fmt, format_args args) -\u2060>\u00a0std::string;
template <detail::fixed_string\u00a0Str>\nconstexpr auto operator\"\"_a();
"},{"location":"api/#utilities","title":"Utilities","text":"
template <typename T>\nauto ptr(T p) -\u2060>\u00a0const void*;
Converts p
to const void*
for pointer formatting.
Example:
auto s = fmt::format(\"{}\", fmt::ptr(p));\n
template <typename Enum>\nconstexpr auto underlying(Enum e) -\u2060>\u00a0underlying_t<Enum>;
Converts e
to the underlying type.
Example:
enum class color { red, green, blue };\nauto s = fmt::format(\"{}\", fmt::underlying(color::red));\n
template <typename T>\nauto to_string(const T& value) -\u2060>\u00a0std::string;
template <typename T>\nauto group_digits(T value) -\u2060>\u00a0group_digits_view<T>;
Returns a view that formats an integer value using ',' as a locale-independent thousands separator.
Example:
fmt::print(\"{}\", fmt::group_digits(12345));\n// Output: \"12,345\"\n
template <typename T>\nclass detail::buffer;
A contiguous memory buffer with an optional growing ability. It is an internal class and shouldn't be used directly, only via memory_buffer
.
constexpr auto size() -\u2060>\u00a0size_t;
Returns the size of this buffer.
constexpr auto capacity() -\u2060>\u00a0size_t;
Returns the capacity of this buffer.
auto data() -\u2060>\u00a0T*;
Returns a pointer to the buffer data (not null-terminated).
void clear();
Clears this buffer.
void append(const U* begin, const U* end);
Appends data to the end of the buffer.
template <typename T, size_t\u00a0SIZE, typename Allocator>\nclass basic_memory_buffer;
A dynamically growing memory buffer for trivially copyable/constructible types with the first SIZE
elements stored in the object itself. Most commonly used via the memory_buffer
alias for char
.
Example:
auto out = fmt::memory_buffer();\nfmt::format_to(std::back_inserter(out), \"The answer is {}.\", 42);\n
This will append \"The answer is 42.\" to out
. The buffer content can be converted to std::string
with to_string(out)
.
basic_memory_buffer(basic_memory_buffer&& other);
Constructs a basic_memory_buffer
object moving the content of the other object to it.
auto operator=(basic_memory_buffer&& other) -\u2060>\u00a0basic_memory_buffer&;
Moves the content of the other basic_memory_buffer
object to this one.
void resize(size_t count);
Resizes the buffer to contain count
elements. If T is a POD type new elements may not be initialized.
void reserve(size_t new_capacity);
Increases the buffer capacity to new_capacity
.
"},{"location":"api/#system-errors","title":"System Errors","text":"
{fmt} does not use errno
to communicate errors to the user, but it may call system functions which set errno
. Users should not make any assumptions about the value of errno
being preserved by library functions.
template <typename...\u00a0T>\nauto system_error(int error_code, format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::system_error;
Constructs std::system_error
with a message formatted with fmt::format(fmt, args...)
. error_code
is a system error code as given by errno
.
Example:
// This throws std::system_error with the description\n// cannot open file 'madeup': No such file or directory\n// or similar (system message may vary).\nconst char* filename = \"madeup\";\nFILE* file = fopen(filename, \"r\");\nif (!file)\n throw fmt::system_error(errno, \"cannot open file '{}'\", filename);\n
void format_system_error(detail::buffer<char>& out, int error_code, const char* message);
Formats an error message for an error returned by an operating system or a language runtime, for example a file opening error, and writes it to out
. The format is the same as the one used by std::system_error(ec, message)
where ec
is std::error_code(error_code, std::generic_category())
. It is implementation-defined but normally looks like:
<message>: <system-message>\n
where <message>
is the passed message and <system-message>
is the system message corresponding to the error code. error_code
is a system error code as given by errno
.
"},{"location":"api/#custom-allocators","title":"Custom Allocators","text":"
The {fmt} library supports custom dynamic memory allocators. A custom allocator class can be specified as a template argument to fmt::basic_memory_buffer
:
using custom_memory_buffer = \n fmt::basic_memory_buffer<char, fmt::inline_buffer_size, custom_allocator>;
It is also possible to write a formatting function that uses a custom allocator:
using custom_string =\n std::basic_string<char, std::char_traits<char>, custom_allocator>;\n\nauto vformat(custom_allocator alloc, fmt::string_view fmt,\n fmt::format_args args) -> custom_string {\n auto buf = custom_memory_buffer(alloc);\n fmt::vformat_to(std::back_inserter(buf), fmt, args);\n return custom_string(buf.data(), buf.size(), alloc);\n}\n\ntemplate <typename ...Args>\nauto format(custom_allocator alloc, fmt::string_view fmt,\n const Args& ... args) -> custom_string {\n return vformat(alloc, fmt, fmt::make_format_args(args...));\n}
The allocator will be used for the output container only. Formatting functions normally don't do any allocations for built-in and string types except for non-default floating-point formatting that occasionally falls back on sprintf
.
"},{"location":"api/#locale","title":"Locale","text":"
All formatting is locale-independent by default. Use the 'L'
format specifier to insert the appropriate number separator characters from the locale:
#include <fmt/core.h>\n#include <locale>\n\nstd::locale::global(std::locale(\"en_US.UTF-8\"));\nauto s = fmt::format(\"{:L}\", 1000000); // s == \"1,000,000\"
fmt/format.h
provides the following overloads of formatting functions that take std::locale
as a parameter. The locale type is a template parameter to avoid the expensive <locale>
include.
template <typename...\u00a0T>\nauto format(detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::string;
template <typename OutputIt, typename...\u00a0T>\nauto format_to(OutputIt out, detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0OutputIt;
template <typename...\u00a0T>\nauto formatted_size(detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0size_t;
"},{"location":"api/#legacy-compile-time-checks","title":"Legacy Compile-Time Checks","text":"
FMT_STRING
enables compile-time checks on older compilers. It requires C++14 or later and is a no-op in C++11.
FMT_STRING(s)
Constructs a compile-time format string from a string literal s
.
Example:
// A compile-time error because 'd' is an invalid specifier for strings.\nstd::string s = fmt::format(FMT_STRING(\"{:d}\"), \"foo\");\n
To force the use of legacy compile-time checks, define the preprocessor variable FMT_ENFORCE_COMPILE_STRING
. When set, functions accepting FMT_STRING
will fail to compile with regular strings.
"},{"location":"api/#range-and-tuple-formatting","title":"Range and Tuple Formatting","text":"
fmt/ranges.h
provides formatting support for ranges and tuples:
#include <fmt/ranges.h>\n\nfmt::print(\"{}\", std::tuple<char, int>{'a', 42});\n// Output: ('a', 42)
Using fmt::join
, you can separate tuple elements with a custom separator:
#include <fmt/ranges.h>\n\nauto t = std::tuple<int, char>{1, 'a'};\nfmt::print(\"{}\", fmt::join(t, \", \"));\n// Output: 1, a
template <typename Range>\nauto join(Range&& r, string_view sep) -\u2060>\u00a0join_view<decltype(detail::range_begin(r)), decltype(detail::range_end(r))>;
Returns a view that formats range
with elements separated by sep
.
Example:
auto v = std::vector<int>{1, 2, 3};\nfmt::print(\"{}\", fmt::join(v, \", \"));\n// Output: 1, 2, 3\n
fmt::join
applies passed format specifiers to the range elements:
fmt::print(\"{:02}\", fmt::join(v, \", \"));\n// Output: 01, 02, 03\n
template <typename It, typename Sentinel>\nauto join(It begin, Sentinel end, string_view sep) -\u2060>\u00a0join_view<It, Sentinel>;
Returns a view that formats the iterator range [begin, end)
with elements separated by sep
.
template <typename T>\nauto join(std::initializer_list<T> list, string_view sep) -\u2060>\u00a0join_view<const T*, const T*>;
Returns an object that formats std::initializer_list
with elements separated by sep
.
Example:
fmt::print(\"{}\", fmt::join({1, 2, 3}, \", \"));\n// Output: \"1, 2, 3\"\n
"},{"location":"api/#date-and-time-formatting","title":"Date and Time Formatting","text":"
fmt/chrono.h
provides formatters for
std::chrono::duration
std::chrono::time_point
std::tm
The format syntax is described in Chrono Format Specifications.
Example:
#include <fmt/chrono.h>\n\nint main() {\n std::time_t t = std::time(nullptr);\n\n fmt::print(\"The date is {:%Y-%m-%d}.\", fmt::localtime(t));\n // Output: The date is 2020-11-07.\n // (with 2020-11-07 replaced by the current date)\n\n using namespace std::literals::chrono_literals;\n\n fmt::print(\"Default format: {} {}\\n\", 42s, 100ms);\n // Output: Default format: 42s 100ms\n\n fmt::print(\"strftime-like format: {:%H:%M:%S}\\n\", 3h + 15min + 30s);\n // Output: strftime-like format: 03:15:30\n}
auto localtime(std::time_t time) -\u2060>\u00a0std::tm;
Converts given time since epoch as std::time_t
value into calendar time, expressed in local time. Unlike std::localtime
, this function is thread-safe on most platforms.
auto gmtime(std::time_t time) -\u2060>\u00a0std::tm;
Converts given time since epoch as std::time_t
value into calendar time, expressed in Coordinated Universal Time (UTC). Unlike std::gmtime
, this function is thread-safe on most platforms.
"},{"location":"api/#standard-library-types-formatting","title":"Standard Library Types Formatting","text":"
fmt/std.h
provides formatters for:
std::atomic
std::atomic_flag
std::bitset
std::error_code
std::exception
std::filesystem::path
std::monostate
std::optional
std::source_location
std::thread::id
std::variant
template <typename T, typename Deleter>\nauto ptr(const std::unique_ptr<T, Deleter>& p) -\u2060>\u00a0const void*;
template <typename T>\nauto ptr(const std::shared_ptr<T>& p) -\u2060>\u00a0const void*;
"},{"location":"api/#formatting-variants","title":"Formatting Variants","text":"
A std::variant
is only formattable if every variant alternative is formattable, and requires the __cpp_lib_variant
library feature.
Example:
#include <fmt/std.h>\n\nfmt::print(\"{}\", std::variant<char, float>('x'));\n// Output: variant('x')\n\nfmt::print(\"{}\", std::variant<std::monostate, char>());\n// Output: variant(monostate)
"},{"location":"api/#format-string-compilation","title":"Format String Compilation","text":"
fmt/compile.h
provides format string compilation enabled via the FMT_COMPILE
macro or the _cf
user-defined literal defined in namespace fmt::literals
. Format strings marked with FMT_COMPILE
or _cf
are parsed, checked and converted into efficient formatting code at compile-time. This supports arguments of built-in and string types as well as user-defined types with format
functions taking the format context type as a template parameter in their formatter
specializations. For example:
template <> struct fmt::formatter<point> {\n constexpr auto parse(format_parse_context& ctx);\n\n template <typename FormatContext>\n auto format(const point& p, FormatContext& ctx) const;\n};
Format string compilation can generate more binary code compared to the default API and is only recommended in places where formatting is a performance bottleneck.
FMT_COMPILE(s)
Converts a string literal s
into a format string that will be parsed at compile time and converted into efficient formatting code. Requires C++17 constexpr if
compiler support.
Example:
// Converts 42 into std::string using the most efficient method and no\n// runtime format string processing.\nstd::string s = fmt::format(FMT_COMPILE(\"{}\"), 42);\n
template <detail::fixed_string\u00a0Str>\nconstexpr auto operator\"\"_cf();
"},{"location":"api/#terminal-colors-and-text-styles","title":"Terminal Colors and Text Styles","text":"
fmt/color.h
provides support for terminal color and text style output.
template <typename...\u00a0T>\nvoid print(const text_style& ts, format_string<T...> fmt, T&&... args);
Formats a string and prints it to stdout using ANSI escape sequences to specify text formatting.
Example:
fmt::print(fmt::emphasis::bold | fg(fmt::color::red),\n \"Elapsed time: {0:.2f} seconds\", 1.23);\n
auto fg(detail::color_type foreground) -\u2060>\u00a0text_style;
Creates a text style from the foreground (text) color.
auto bg(detail::color_type background) -\u2060>\u00a0text_style;
Creates a text style from the background color.
template <typename T>\nauto styled(const T& value, text_style ts) -\u2060>\u00a0detail::styled_arg<remove_cvref_t<T>>;
Returns an argument that will be formatted using ANSI escape sequences, to be used in a formatting function.
Example:
fmt::print(\"Elapsed time: {0:.2f} seconds\",\n fmt::styled(1.23, fmt::fg(fmt::color::green) |\n fmt::bg(fmt::color::blue)));\n
"},{"location":"api/#system-apis","title":"System APIs","text":"
class ostream;
A fast buffered output stream for writing from a single thread. Writing from multiple threads without external synchronization may result in a data race.
void print(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file.
template <typename...\u00a0T>\nauto windows_error(int error_code, string_view message, const T&... args) -\u2060>\u00a0std::system_error;
Constructs a std::system_error
object with the description of the form
<message>: <system-message>\n
where <message>
is the formatted message and <system-message>
is the system message corresponding to the error code. error_code
is a Windows error code as given by GetLastError
. If error_code
is not a valid error code such as -1, the system message will look like \"error -1\".
Example:
// This throws a system_error with the description\n// cannot open file 'madeup': The system cannot find the file\n
specified. // or similar (system message may vary). const char *filename = \"madeup\"; LPOFSTRUCT of = LPOFSTRUCT(); HFILE file = OpenFile(filename, &of, OF_READ); if (file == HFILE_ERROR) { throw fmt::windows_error(GetLastError(), \"cannot open file '{}'\", filename); }
"},{"location":"api/#stdostream-support","title":"
std::ostream
Support","text":"
fmt/ostream.h
provides std::ostream
support including formatting of user-defined types that have an overloaded insertion operator (operator<<
). In order to make a type formattable via std::ostream
you should provide a formatter
specialization inherited from ostream_formatter
:
#include <fmt/ostream.h>\n\nstruct date {\n int year, month, day;\n\n friend std::ostream& operator<<(std::ostream& os, const date& d) {\n return os << d.year << '-' << d.month << '-' << d.day;\n }\n};\n\ntemplate <> struct fmt::formatter<date> : ostream_formatter {};\n\nstd::string s = fmt::format(\"The date is {}\", date{2012, 12, 9});\n// s == \"The date is 2012-12-9\"
template <typename T>\nconstexpr auto streamed(const T& value) -\u2060>\u00a0detail::streamed_view<T>;
Returns a view that formats value
via an ostream operator<<
.
Example:
fmt::print(\"Current thread id: {}\\n\",\n fmt::streamed(std::this_thread::get_id()));\n
template <typename...\u00a0T>\nvoid print(std::ostream& os, format_string<T...> fmt, T&&... args);
Prints formatted data to the stream os
.
Example:
fmt::print(cerr, \"Don't {}!\", \"panic\");\n
"},{"location":"api/#dynamic-argument-lists","title":"Dynamic Argument Lists","text":"
The header fmt/args.h
provides dynamic_format_arg_store
, a builder-like API that can be used to construct format argument lists dynamically.
template <typename Context>\nclass dynamic_format_arg_store;
A dynamic list of formatting arguments with storage.
It can be implicitly converted into fmt::basic_format_args
for passing into type-erased formatting functions such as fmt::vformat
.
void push_back(const T& arg);
Adds an argument into the dynamic store for later passing to a formatting function.
Note that custom types and string types (but not string views) are copied into the store dynamically allocating memory if necessary.
Example:
fmt::dynamic_format_arg_store<fmt::format_context> store;\nstore.push_back(42);\nstore.push_back(\"abc\");\nstore.push_back(1.5f);\nstd::string result = fmt::vformat(\"{} and {} and {}\", store);\n
void push_back(std::reference_wrapper<T> arg);
Adds a reference to the argument into the dynamic store for later passing to a formatting function.
Example:
fmt::dynamic_format_arg_store<fmt::format_context> store;\nchar band[] = \"Rolling Stones\";\nstore.push_back(std::cref(band));\nband[9] = 'c'; // Changing str affects the output.\nstd::string result = fmt::vformat(\"{}\", store);\n// result == \"Rolling Scones\"\n
void push_back(const detail::named_arg<char_type, T>& arg);
Adds named argument into the dynamic store for later passing to a formatting function. std::reference_wrapper
is supported to avoid copying of the argument. The name is always copied into the store.
void clear();
Erase all elements from the store.
void reserve(size_t new_cap, size_t new_cap_named);
Reserves space to store at least new_cap
arguments including new_cap_named
named arguments.
"},{"location":"api/#safe-printf","title":"Safe
printf
","text":"
The header fmt/printf.h
provides printf
-like formatting functionality. The following functions use printf format string syntax with the POSIX extension for positional arguments. Unlike their standard counterparts, the fmt
functions are type-safe and throw an exception if an argument type doesn't match its format specification.
template <typename...\u00a0T>\nauto printf(string_view fmt, const T&... args) -\u2060>\u00a0int;
Formats args
according to specifications in fmt
and writes the output to stdout
.
Example:
fmt::printf(\"Elapsed time: %.2f seconds\", 1.23);
template <typename S, typename...\u00a0T, typename Char>\nauto fprintf(std::FILE* f, const S& fmt, const T&... args) -\u2060>\u00a0int;
Formats args
according to specifications in fmt
and writes the output to f
.
Example:
fmt::fprintf(stderr, \"Don't %s!\", \"panic\");\n
template <typename S, typename...\u00a0T, typename Char>\nauto sprintf(const S& fmt, const T&... args) -\u2060>\u00a0std::basic_string<Char>;
Formats args
according to specifications in fmt
and returns the result as as string.
Example:
std::string message = fmt::sprintf(\"The answer is %d\", 42);\n
"},{"location":"api/#wide-strings","title":"Wide Strings","text":"
The optional header fmt/xchar.h
provides support for wchar_t
and exotic character types.
template <typename T>\nstruct is_char;
using wstring_view = basic_string_view<wchar_t>;
using wformat_context = buffered_context<wchar_t>;
template <typename T>\nauto to_wstring(const T& value) -\u2060>\u00a0std::wstring;
Converts value
to std::wstring
using the default format for type T
.
"},{"location":"api/#compatibility-with-c20-stdformat","title":"Compatibility with C++20
std::format
","text":"
{fmt} implements nearly all of the C++20 formatting library with the following differences:
- Names are defined in the
fmt
namespace instead of std
to avoid collisions with standard library implementations. - Width calculation doesn't use grapheme clusterization. The latter has been implemented in a separate branch but hasn't been integrated yet.
"},{"location":"get-started/","title":"Get Started","text":"
Compile and run {fmt} examples online with Compiler Explorer.
{fmt} is compatible with any build system. The next section describes its usage with CMake, while the Build Systems section covers the rest.
"},{"location":"get-started/#cmake","title":"CMake","text":"
{fmt} provides two CMake targets: fmt::fmt
for the compiled library and fmt::fmt-header-only
for the header-only library. It is recommended to use the compiled library for improved build times.
There are three primary ways to use {fmt} with CMake:
-
FetchContent: Starting from CMake 3.11, you can use FetchContent
to automatically download {fmt} as a dependency at configure time:
include(FetchContent)\n\nFetchContent_Declare(\n fmt\n GIT_REPOSITORY https://github.com/fmtlib/fmt\n GIT_TAG e69e5f977d458f2650bb346dadf2ad30c5320281) # 10.2.1\nFetchContent_MakeAvailable(fmt)\n\ntarget_link_libraries(<your-target> fmt::fmt)
-
Installed: You can find and use an installed version of {fmt} in your CMakeLists.txt
file as follows:
find_package(fmt)\ntarget_link_libraries(<your-target> fmt::fmt)
-
Embedded: You can add the {fmt} source tree to your project and include it in your CMakeLists.txt
file:
add_subdirectory(fmt)\ntarget_link_libraries(<your-target> fmt::fmt)
"},{"location":"get-started/#installation","title":"Installation","text":""},{"location":"get-started/#debianubuntu","title":"Debian/Ubuntu","text":"
To install {fmt} on Debian, Ubuntu, or any other Debian-based Linux distribution, use the following command:
apt install libfmt-dev
"},{"location":"get-started/#homebrew","title":"Homebrew","text":"
Install {fmt} on macOS using Homebrew:
brew install fmt
"},{"location":"get-started/#conda","title":"Conda","text":"
Install {fmt} on Linux, macOS, and Windows with Conda, using its conda-forge package:
conda install -c conda-forge fmt
"},{"location":"get-started/#vcpkg","title":"vcpkg","text":"
Download and install {fmt} using the vcpkg package manager:
git clone https://github.com/Microsoft/vcpkg.git\ncd vcpkg\n./bootstrap-vcpkg.sh\n./vcpkg integrate install\n./vcpkg install fmt
"},{"location":"get-started/#building-from-source","title":"Building from Source","text":"
CMake works by generating native makefiles or project files that can be used in the compiler environment of your choice. The typical workflow starts with:
mkdir build # Create a directory to hold the build output.\ncd build\ncmake .. # Generate native build scripts.
run in the fmt
repository.
If you are on a Unix-like system, you should now see a Makefile in the current directory. Now you can build the library by running make
.
Once the library has been built you can invoke make test
to run the tests.
You can control generation of the make test
target with the FMT_TEST
CMake option. This can be useful if you include fmt as a subdirectory in your project but don't want to add fmt's tests to your test
target.
To build a shared library set the BUILD_SHARED_LIBS
CMake variable to TRUE
:
cmake -DBUILD_SHARED_LIBS=TRUE ..
To build a static library with position-independent code (e.g. for linking it into another shared library such as a Python extension), set the CMAKE_POSITION_INDEPENDENT_CODE
CMake variable to TRUE
:
cmake -DCMAKE_POSITION_INDEPENDENT_CODE=TRUE ..
After building the library you can install it on a Unix-like system by running sudo make install
.
"},{"location":"get-started/#building-the-docs","title":"Building the Docs","text":"
To build the documentation you need the following software installed on your system:
- Python
- Doxygen
- MkDocs with
mkdocs-material
, mkdocstrings
, pymdown-extensions
and mike
First generate makefiles or project files using CMake as described in the previous section. Then compile the doc
target/project, for example:
make doc
This will generate the HTML documentation in doc/html
.
"},{"location":"get-started/#build-systems","title":"Build Systems","text":""},{"location":"get-started/#build2","title":"build2","text":"
You can use build2, a dependency manager and a build system, to use {fmt}.
Currently this package is available in these package repositories:
- https://cppget.org/fmt/ for released and published versions.
- https://github.com/build2-packaging/fmt for unreleased or custom versions.
Usage:
build2
package name: fmt
- Library target name:
lib{fmt}
To make your build2
project depend on fmt
:
-
Add one of the repositories to your configurations, or in your repositories.manifest
, if not already there:
:\nrole: prerequisite\nlocation: https://pkg.cppget.org/1/stable
-
Add this package as a dependency to your manifest
file (example for version 10):
depends: fmt ~10.0.0
-
Import the target and use it as a prerequisite to your own target using fmt
in the appropriate buildfile
:
import fmt = fmt%lib{fmt}\nlib{mylib} : cxx{**} ... $fmt
Then build your project as usual with b
or bdep update
.
"},{"location":"get-started/#meson","title":"Meson","text":"
Meson WrapDB includes an fmt
package.
Usage:
- Install the
fmt
subproject from the WrapDB by running:meson wrap install fmt
from the root of your project.
-
In your project's meson.build
file, add an entry for the new subproject:
fmt = subproject('fmt')\nfmt_dep = fmt.get_variable('fmt_dep')
-
Include the new dependency object to link with fmt:
my_build_target = executable(\n 'name', 'src/main.cc', dependencies: [fmt_dep])
Options:
If desired, {fmt} can be built as a static library, or as a header-only library.
For a static build, use the following subproject definition:
fmt = subproject('fmt', default_options: 'default_library=static')\nfmt_dep = fmt.get_variable('fmt_dep')
For the header-only version, use:
fmt = subproject('fmt')\nfmt_dep = fmt.get_variable('fmt_header_only_dep')
"},{"location":"get-started/#android-ndk","title":"Android NDK","text":"
{fmt} provides Android.mk file that can be used to build the library with Android NDK.
"},{"location":"get-started/#other","title":"Other","text":"
To use the {fmt} library with any other build system, add include/fmt/base.h
, include/fmt/format.h
, include/fmt/format-inl.h
, src/format.cc
and optionally other headers from a release archive or the git repository to your project, add include
to include directories and make sure src/format.cc
is compiled and linked with your code.
"},{"location":"syntax/","title":"Format String Syntax","text":"
Formatting functions such as fmt::format
and fmt::print
use the same format string syntax described in this section.
Format strings contain \"replacement fields\" surrounded by curly braces {}
. Anything that is not contained in braces is considered literal text, which is copied unchanged to the output. If you need to include a brace character in the literal text, it can be escaped by doubling: {{
and }}
.
The grammar for a replacement field is as follows:
replacement_field ::= \"{\" [arg_id] [\":\" (format_spec | chrono_format_spec)] \"}\"\narg_id ::= integer | identifier\ninteger ::= digit+\ndigit ::= \"0\"...\"9\"\nidentifier ::= id_start id_continue*\nid_start ::= \"a\"...\"z\" | \"A\"...\"Z\" | \"_\"\nid_continue ::= id_start | digit
\n
In less formal terms, the replacement field can start with an arg_id that specifies the argument whose value is to be formatted and inserted into the output instead of the replacement field. The arg_id is optionally followed by a format_spec, which is preceded by a colon ':'
. These specify a non-default format for the replacement value.
See also the Format Specification Mini-Language section.
If the numerical arg_ids in a format string are 0, 1, 2, ... in sequence, they can all be omitted (not just some) and the numbers 0, 1, 2, ... will be automatically inserted in that order.
Named arguments can be referred to by their names or indices.
Some simple format string examples:
\"First, thou shalt count to {0}\" // References the first argument\n\"Bring me a {}\" // Implicitly references the first argument\n\"From {} to {}\" // Same as \"From {0} to {1}\"\n
The format_spec field contains a specification of how the value should be presented, including such details as field width, alignment, padding, decimal precision and so on. Each value type can define its own \"formatting mini-language\" or interpretation of the format_spec.
Most built-in types support a common formatting mini-language, which is described in the next section.
A format_spec field can also include nested replacement fields in certain positions within it. These nested replacement fields can contain only an argument id; format specifications are not allowed. This allows the formatting of a value to be dynamically specified.
See the Format Examples section for some examples.
"},{"location":"syntax/#format-specification-mini-language","title":"Format Specification Mini-Language","text":"
\"Format specifications\" are used within replacement fields contained within a format string to define how individual values are presented. Each formattable type may define how the format specification is to be interpreted.
Most built-in types implement the following options for format specifications, although some of the formatting options are only supported by the numeric types.
The general form of a standard format specifier is:
format_spec ::= [[fill]align][sign][\"#\"][\"0\"][width][\".\" precision][\"L\"][type]\nfill ::= <a character other than '{' or '}'>\nalign ::= \"<\" | \">\" | \"^\"\nsign ::= \"+\" | \"-\" | \" \"\nwidth ::= integer | \"{\" [arg_id] \"}\"\nprecision ::= integer | \"{\" [arg_id] \"}\"\ntype ::= \"a\" | \"A\" | \"b\" | \"B\" | \"c\" | \"d\" | \"e\" | \"E\" | \"f\" | \"F\" |\n \"g\" | \"G\" | \"o\" | \"p\" | \"s\" | \"x\" | \"X\" | \"?\"
\n
The fill character can be any Unicode code point other than '{'
or '}'
. The presence of a fill character is signaled by the character following it, which must be one of the alignment options. If the second character of format_spec is not a valid alignment option, then it is assumed that both the fill character and the alignment option are absent.
The meaning of the various alignment options is as follows:
Option Meaning
'<'
Forces the field to be left-aligned within the available space (this is the default for most objects).
'>'
Forces the field to be right-aligned within the available space (this is the default for numbers).
'^'
Forces the field to be centered within the available space.
Note that unless a minimum field width is defined, the field width will always be the same size as the data to fill it, so that the alignment option has no meaning in this case.
The sign option is only valid for floating point and signed integer types, and can be one of the following:
Option Meaning
'+'
Indicates that a sign should be used for both nonnegative as well as negative numbers.
'-'
Indicates that a sign should be used only for negative numbers (this is the default behavior). space Indicates that a leading space should be used on nonnegative numbers, and a minus sign on negative numbers.
The '#'
option causes the \"alternate form\" to be used for the conversion. The alternate form is defined differently for different types. This option is only valid for integer and floating-point types. For integers, when binary, octal, or hexadecimal output is used, this option adds the prefix respective \"0b\"
(\"0B\"
), \"0\"
, or \"0x\"
(\"0X\"
) to the output value. Whether the prefix is lower-case or upper-case is determined by the case of the type specifier, for example, the prefix \"0x\"
is used for the type 'x'
and \"0X\"
is used for 'X'
. For floating-point numbers the alternate form causes the result of the conversion to always contain a decimal-point character, even if no digits follow it. Normally, a decimal-point character appears in the result of these conversions only if a digit follows it. In addition, for 'g'
and 'G'
conversions, trailing zeros are not removed from the result.
width is a decimal integer defining the minimum field width. If not specified, then the field width will be determined by the content.
Preceding the width field by a zero ('0'
) character enables sign-aware zero-padding for numeric types. It forces the padding to be placed after the sign or base (if any) but before the digits. This is used for printing fields in the form \"+000000120\". This option is only valid for numeric types and it has no effect on formatting of infinity and NaN. This option is ignored when any alignment specifier is present.
The precision is a decimal number indicating how many digits should be displayed after the decimal point for a floating-point value formatted with 'f'
and 'F'
, or before and after the decimal point for a floating-point value formatted with 'g'
or 'G'
. For non-number types the field indicates the maximum field size - in other words, how many characters will be used from the field content. The precision is not allowed for integer, character, Boolean, and pointer values. Note that a C string must be null-terminated even if precision is specified.
The 'L'
option uses the current locale setting to insert the appropriate number separator characters. This option is only valid for numeric types.
Finally, the type determines how the data should be presented.
The available string presentation types are:
Type Meaning
's'
String format. This is the default type for strings and may be omitted.
'?'
Debug format. The string is quoted and special characters escaped. none The same as
's'
.
The available character presentation types are:
Type Meaning
'c'
Character format. This is the default type for characters and may be omitted.
'?'
Debug format. The character is quoted and special characters escaped. none The same as
'c'
.
The available integer presentation types are:
Type Meaning
'b'
Binary format. Outputs the number in base 2. Using the
'#'
option with this type adds the prefix
\"0b\"
to the output value.
'B'
Binary format. Outputs the number in base 2. Using the
'#'
option with this type adds the prefix
\"0B\"
to the output value.
'c'
Character format. Outputs the number as a character.
'd'
Decimal integer. Outputs the number in base 10.
'o'
Octal format. Outputs the number in base 8.
'x'
Hex format. Outputs the number in base 16, using lower-case letters for the digits above 9. Using the
'#'
option with this type adds the prefix
\"0x\"
to the output value.
'X'
Hex format. Outputs the number in base 16, using upper-case letters for the digits above 9. Using the
'#'
option with this type adds the prefix
\"0X\"
to the output value. none The same as
'd'
.
Integer presentation types can also be used with character and Boolean values with the only exception that 'c'
cannot be used with bool
. Boolean values are formatted using textual representation, either true
or false
, if the presentation type is not specified.
The available presentation types for floating-point values are:
Type Meaning
'a'
Hexadecimal floating point format. Prints the number in base 16 with prefix
\"0x\"
and lower-case letters for digits above 9. Uses
'p'
to indicate the exponent.
'A'
Same as
'a'
except it uses upper-case letters for the prefix, digits above 9 and to indicate the exponent.
'e'
Exponent notation. Prints the number in scientific notation using the letter 'e' to indicate the exponent.
'E'
Exponent notation. Same as
'e'
except it uses an upper-case
'E'
as the separator character.
'f'
Fixed point. Displays the number as a fixed-point number.
'F'
Fixed point. Same as
'f'
, but converts
nan
to
NAN
and
inf
to
INF
.
'g'
General format. For a given precision p >= 1
, this rounds the number to p
significant digits and then formats the result in either fixed-point format or in scientific notation, depending on its magnitude.
A precision of 0
is treated as equivalent to a precision of 1
.
'G'
General format. Same as
'g'
except switches to
'E'
if the number gets too large. The representations of infinity and NaN are uppercased, too. none Similar to
'g'
, except that the default precision is as high as needed to represent the particular value.
The available presentation types for pointers are:
Type Meaning
'p'
Pointer format. This is the default type for pointers and may be omitted. none The same as
'p'
."},{"location":"syntax/#chrono-format-specifications","title":"Chrono Format Specifications","text":"
Format specifications for chrono duration and time point types as well as std::tm
have the following syntax:
chrono_format_spec ::= [[fill]align][width][\".\" precision][chrono_specs]\nchrono_specs ::= conversion_spec |\n chrono_specs (conversion_spec | literal_char)\nconversion_spec ::= \"%\" [padding_modifier] [locale_modifier] chrono_type\nliteral_char ::= <a character other than '{', '}' or '%'>\npadding_modifier ::= \"-\" | \"_\" | \"0\"\nlocale_modifier ::= \"E\" | \"O\"\nchrono_type ::= \"a\" | \"A\" | \"b\" | \"B\" | \"c\" | \"C\" | \"d\" | \"D\" | \"e\" |\n \"F\" | \"g\" | \"G\" | \"h\" | \"H\" | \"I\" | \"j\" | \"m\" | \"M\" |\n \"n\" | \"p\" | \"q\" | \"Q\" | \"r\" | \"R\" | \"S\" | \"t\" | \"T\" |\n \"u\" | \"U\" | \"V\" | \"w\" | \"W\" | \"x\" | \"X\" | \"y\" | \"Y\" |\n \"z\" | \"Z\" | \"%\"
\n
Literal chars are copied unchanged to the output. Precision is valid only for std::chrono::duration
types with a floating-point representation type.
The available presentation types (chrono_type) are:
Type Meaning
'a'
The abbreviated weekday name, e.g. \"Sat\". If the value does not contain a valid weekday, an exception of type
format_error
is thrown.
'A'
The full weekday name, e.g. \"Saturday\". If the value does not contain a valid weekday, an exception of type
format_error
is thrown.
'b'
The abbreviated month name, e.g. \"Nov\". If the value does not contain a valid month, an exception of type
format_error
is thrown.
'B'
The full month name, e.g. \"November\". If the value does not contain a valid month, an exception of type
format_error
is thrown.
'c'
The date and time representation, e.g. \"Sat Nov 12 22:04:00 1955\". The modified command
%Ec
produces the locale's alternate date and time representation.
'C'
The year divided by 100 using floored division, e.g. \"19\". If the result is a single decimal digit, it is prefixed with 0. The modified command
%EC
produces the locale's alternative representation of the century.
'd'
The day of month as a decimal number. If the result is a single decimal digit, it is prefixed with 0. The modified command
%Od
produces the locale's alternative representation.
'D'
Equivalent to
%m/%d/%y
, e.g. \"11/12/55\".
'e'
The day of month as a decimal number. If the result is a single decimal digit, it is prefixed with a space. The modified command
%Oe
produces the locale's alternative representation.
'F'
Equivalent to
%Y-%m-%d
, e.g. \"1955-11-12\".
'g'
The last two decimal digits of the ISO week-based year. If the result is a single digit it is prefixed by 0.
'G'
The ISO week-based year as a decimal number. If the result is less than four digits it is left-padded with 0 to four digits.
'h'
Equivalent to
%b
, e.g. \"Nov\".
'H'
The hour (24-hour clock) as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OH
produces the locale's alternative representation.
'I'
The hour (12-hour clock) as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OI
produces the locale's alternative representation.
'j'
If the type being formatted is a specialization of duration, the decimal number of days without padding. Otherwise, the day of the year as a decimal number. Jan 1 is 001. If the result is less than three digits, it is left-padded with 0 to three digits.
'm'
The month as a decimal number. Jan is 01. If the result is a single digit, it is prefixed with 0. The modified command
%Om
produces the locale's alternative representation.
'M'
The minute as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OM
produces the locale's alternative representation.
'n'
A new-line character.
'p'
The AM/PM designations associated with a 12-hour clock.
'q'
The duration's unit suffix.
'Q'
The duration's numeric value (as if extracted via
.count()
).
'r'
The 12-hour clock time, e.g. \"10:04:00 PM\".
'R'
Equivalent to
%H:%M
, e.g. \"22:04\".
'S'
Seconds as a decimal number. If the number of seconds is less than 10, the result is prefixed with 0. If the precision of the input cannot be exactly represented with seconds, then the format is a decimal floating-point number with a fixed format and a precision matching that of the precision of the input (or to a microseconds precision if the conversion to floating-point decimal seconds cannot be made within 18 fractional digits). The modified command
%OS
produces the locale's alternative representation.
't'
A horizontal-tab character.
'T'
Equivalent to
%H:%M:%S
.
'u'
The ISO weekday as a decimal number (1-7), where Monday is 1. The modified command
%Ou
produces the locale's alternative representation.
'U'
The week number of the year as a decimal number. The first Sunday of the year is the first day of week 01. Days of the same year prior to that are in week 00. If the result is a single digit, it is prefixed with 0. The modified command
%OU
produces the locale's alternative representation.
'V'
The ISO week-based week number as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OV
produces the locale's alternative representation.
'w'
The weekday as a decimal number (0-6), where Sunday is 0. The modified command
%Ow
produces the locale's alternative representation.
'W'
The week number of the year as a decimal number. The first Monday of the year is the first day of week 01. Days of the same year prior to that are in week 00. If the result is a single digit, it is prefixed with 0. The modified command
%OW
produces the locale's alternative representation.
'x'
The date representation, e.g. \"11/12/55\". The modified command
%Ex
produces the locale's alternate date representation.
'X'
The time representation, e.g. \"10:04:00\". The modified command
%EX
produces the locale's alternate time representation.
'y'
The last two decimal digits of the year. If the result is a single digit it is prefixed by 0. The modified command
%Oy
produces the locale's alternative representation. The modified command
%Ey
produces the locale's alternative representation of offset from
%EC
(year only).
'Y'
The year as a decimal number. If the result is less than four digits it is left-padded with 0 to four digits. The modified command
%EY
produces the locale's alternative full year representation.
'z'
The offset from UTC in the ISO 8601:2004 format. For example -0430 refers to 4 hours 30 minutes behind UTC. If the offset is zero, +0000 is used. The modified commands
%Ez
and
%Oz
insert a
:
between the hours and minutes: -04:30. If the offset information is not available, an exception of type
format_error
is thrown.
'Z'
The time zone abbreviation. If the time zone abbreviation is not available, an exception of type
format_error
is thrown.
'%'
A % character.
Specifiers that have a calendaric component such as 'd'
(the day of month) are valid only for std::tm
and time points but not durations.
The available padding modifiers (padding_modifier) are:
Type Meaning
'-'
Pad a numeric result with spaces.
'_'
Do not pad a numeric result string.
'0'
Pad a numeric result string with zeros.
These modifiers are only supported for the 'H'
, 'I'
, 'M'
, 'S'
, 'U'
, 'V'
, 'W'
, 'm'
, 'j'
, 'Y'
presentation types.
"},{"location":"syntax/#range-format-specifications","title":"Range Format Specifications","text":"
Format specifications for range types have the following syntax:
range_format_spec ::= [\"n\"][range_type][range_underlying_spec]
\n
The 'n'
option formats the range without the opening and closing brackets.
The available presentation types for range_type
are:
Type Meaning none Default format.
's'
String format. The range is formatted as a string.
'?\u2060s'
Debug format. The range is formatted as an escaped string.
If range_type
is 's'
or '?s'
, the range element type must be a character type. The 'n'
option and range_underlying_spec
are mutually exclusive with 's'
and '?s'
.
The range_underlying_spec
is parsed based on the formatter of the range's element type.
By default, a range of characters or strings is printed escaped and quoted. But if any range_underlying_spec
is provided (even if it is empty), then the characters or strings are printed according to the provided specification.
Examples:
fmt::print(\"{}\", std::vector{10, 20, 30});\n// Output: [10, 20, 30]\nfmt::print(\"{::#x}\", std::vector{10, 20, 30});\n// Output: [0xa, 0x14, 0x1e]\nfmt::print(\"{}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: ['h', 'e', 'l', 'l', 'o']\nfmt::print(\"{:n}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: 'h', 'e', 'l', 'l', 'o'\nfmt::print(\"{:s}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: \"hello\"\nfmt::print(\"{:?s}\", std::vector{'h', 'e', 'l', 'l', 'o', '\\n'});\n// Output: \"hello\\n\"\nfmt::print(\"{::}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: [h, e, l, l, o]\nfmt::print(\"{::d}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: [104, 101, 108, 108, 111]\n
"},{"location":"syntax/#format-examples","title":"Format Examples","text":"
This section contains examples of the format syntax and comparison with the printf formatting.
In most of the cases the syntax is similar to the printf formatting, with the addition of the {}
and with :
used instead of %
. For example, \"%03.2f\"
can be translated to \"{:03.2f}\"
.
The new format syntax also supports new and different options, shown in the following examples.
Accessing arguments by position:
fmt::format(\"{0}, {1}, {2}\", 'a', 'b', 'c');\n// Result: \"a, b, c\"\nfmt::format(\"{}, {}, {}\", 'a', 'b', 'c');\n// Result: \"a, b, c\"\nfmt::format(\"{2}, {1}, {0}\", 'a', 'b', 'c');\n// Result: \"c, b, a\"\nfmt::format(\"{0}{1}{0}\", \"abra\", \"cad\"); // arguments' indices can be repeated\n// Result: \"abracadabra\"\n
Aligning the text and specifying a width:
fmt::format(\"{:<30}\", \"left aligned\");\n// Result: \"left aligned \"\nfmt::format(\"{:>30}\", \"right aligned\");\n// Result: \" right aligned\"\nfmt::format(\"{:^30}\", \"centered\");\n// Result: \" centered \"\nfmt::format(\"{:*^30}\", \"centered\"); // use '*' as a fill char\n// Result: \"***********centered***********\"\n
Dynamic width:
fmt::format(\"{:<{}}\", \"left aligned\", 30);\n// Result: \"left aligned \"\n
Dynamic precision:
fmt::format(\"{:.{}f}\", 3.14, 1);\n// Result: \"3.1\"\n
Replacing %+f
, %-f
, and % f
and specifying a sign:
fmt::format(\"{:+f}; {:+f}\", 3.14, -3.14); // show it always\n// Result: \"+3.140000; -3.140000\"\nfmt::format(\"{: f}; {: f}\", 3.14, -3.14); // show a space for positive numbers\n// Result: \" 3.140000; -3.140000\"\nfmt::format(\"{:-f}; {:-f}\", 3.14, -3.14); // show only the minus -- same as '{:f}; {:f}'\n// Result: \"3.140000; -3.140000\"\n
Replacing %x
and %o
and converting the value to different bases:
fmt::format(\"int: {0:d}; hex: {0:x}; oct: {0:o}; bin: {0:b}\", 42);\n// Result: \"int: 42; hex: 2a; oct: 52; bin: 101010\"\n// with 0x or 0 or 0b as prefix:\nfmt::format(\"int: {0:d}; hex: {0:#x}; oct: {0:#o}; bin: {0:#b}\", 42);\n// Result: \"int: 42; hex: 0x2a; oct: 052; bin: 0b101010\"\n
Padded hex byte with prefix and always prints both hex characters:
fmt::format(\"{:#04x}\", 0);\n// Result: \"0x00\"\n
Box drawing using Unicode fill:
fmt::print(\n \"\u250c{0:\u2500^{2}}\u2510\\n\"\n \"\u2502{1: ^{2}}\u2502\\n\"\n \"\u2514{0:\u2500^{2}}\u2518\\n\", \"\", \"Hello, world!\", 20);\n
prints:
\u250c\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510\n\u2502 Hello, world! \u2502\n\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518\n
Using type-specific formatting:
#include <fmt/chrono.h>\n\nauto t = tm();\nt.tm_year = 2010 - 1900;\nt.tm_mon = 7;\nt.tm_mday = 4;\nt.tm_hour = 12;\nt.tm_min = 15;\nt.tm_sec = 58;\nfmt::print(\"{:%Y-%m-%d %H:%M:%S}\", t);\n// Prints: 2010-08-04 12:15:58\n
Using the comma as a thousands separator:
#include <fmt/format.h>\n\nauto s = fmt::format(std::locale(\"en_US.UTF-8\"), \"{:L}\", 1234567890);\n// s == \"1,234,567,890\"\n
"}]}
\ No newline at end of file
+{"config":{"lang":["en"],"separator":"[\\s\\-]+","pipeline":["stopWordFilter"]},"docs":[{"location":"","title":"A modern formatting library","text":"Safety
Inspired by Python's formatting facility, {fmt} provides a safe replacement for the printf
family of functions. Errors in format strings, which are a common source of vulnerabilities in C, are reported at compile time. For example:
fmt::format(\"{:d}\", \"I am not a number\");
will give a compile-time error because
d
is not a valid format specifier for strings. APIs like
fmt::format
prevent buffer overflow errors via automatic memory management. \u2192 Learn more Extensibility
Formatting of most standard types, including all containers, dates, and times is supported out-of-the-box. For example:
fmt::print(\"{}\", std::vector{1, 2, 3});
prints the vector in a JSON-like format:
[1, 2, 3]
You can make your own types formattable and even make compile-time checks work for them. \u2192 Learn more Performance
{fmt} can be anywhere from tens of percent to 20-30 times faster than iostreams and sprintf
, especially for numeric formatting. The library minimizes dynamic memory allocations and can optionally compile format strings to optimal code.
Unicode support
{fmt} provides portable Unicode support on major operating systems with UTF-8 and char
strings. For example:
fmt::print(\"\u0421\u043b\u0430\u0432\u0430 \u0423\u043a\u0440\u0430\u0457\u043d\u0456!\");
will be printed correctly on Linux, macOS, and even Windows console, irrespective of the codepages.
The default is locale-independent, but you can opt into localized formatting and {fmt} makes it work with Unicode, addressing issues in the standard libary.
Fast compilation
The library makes extensive use of type erasure to achieve fast compilation. fmt/base.h
provides a subset of the API with minimal include dependencies and enough functionality to replace all uses of *printf
.
Code using {fmt} is usually several times faster to compile than the equivalent iostreams code, and while printf
compiles faster still, the gap is narrowing.
\u2192 Learn more Small binary footprint
Type erasure is also used to prevent template bloat, resulting in compact per-call binary code. For example, a call to fmt::print
with a single argument is just a few instructions, comparable to printf
despite adding runtime safety, and much smaller than the equivalent iostreams code.
The library itself has small binary footprint and some components such as floating-point formatting can be disabled to make it even smaller for resource-constrained devices.
Portability
{fmt} has a small self-contained codebase with the core consisting of just three headers and no external dependencies.
The library is highly portable and requires only a minimal subset of C++11 features which are available in GCC 4.9, Clang 3.4, MSVC 19.0 (2015) and later. Newer compiler and standard library features are used if available, and enable additional functionality.
Where possible, the output of formatting functions is consistent across platforms.
Open source
{fmt} is in the top hundred open-source C++ libraries on GitHub and has hundreds of all-time contributors.
The library is distributed under a permissive MIT license and is relied upon by many open-source projects, including Blender, PyTorch, Apple's FoundationDB, Windows Terminal, MongoDB, and others.
"},{"location":"api/","title":"API Reference","text":"
The {fmt} library API consists of the following components:
fmt/base.h
: the base API providing main formatting functions for char
/UTF-8 with C++20 compile-time checks and minimal dependencies fmt/format.h
: fmt::format
and other formatting functions as well as locale support fmt/ranges.h
: formatting of ranges and tuples fmt/chrono.h
: date and time formatting fmt/std.h
: formatters for standard library types fmt/compile.h
: format string compilation fmt/color.h
: terminal colors and text styles fmt/os.h
: system APIs fmt/ostream.h
: std::ostream
support fmt/args.h
: dynamic argument lists fmt/printf.h
: safe printf
fmt/xchar.h
: optional wchar_t
support
All functions and types provided by the library reside in namespace fmt
and macros have prefix FMT_
.
"},{"location":"api/#base-api","title":"Base API","text":"
fmt/base.h
defines the base API which provides main formatting functions for char
/UTF-8 with C++20 compile-time checks. It has minimal include dependencies for better compile times. This header is only beneficial when using {fmt} as a library (the default) and not in the header-only mode. It also provides formatter
specializations for the following types:
int
, long long
, unsigned
, unsigned long long
float
, double
, long double
bool
char
const char*
, fmt::string_view
const void*
The following functions use format string syntax similar to that of str.format in Python. They take fmt and args as arguments.
fmt is a format string that contains literal text and replacement fields surrounded by braces {}
. The fields are replaced with formatted arguments in the resulting string. fmt::format_string
is a format string which can be implicitly constructed from a string literal or a constexpr
string and is checked at compile time in C++20. To pass a runtime format string wrap it in fmt::runtime
.
args is an argument list representing objects to be formatted.
I/O errors are reported as std::system_error
exceptions unless specified otherwise.
template <typename...\u00a0T>\nvoid print(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to stdout
.
Example:
fmt::print(\"The answer is {}.\", 42);\n
template <typename...\u00a0T>\nvoid print(FILE* f, format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file f
.
Example:
fmt::print(stderr, \"Don't {}!\", \"panic\");\n
template <typename...\u00a0T>\nvoid println(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to stdout
followed by a newline.
template <typename...\u00a0T>\nvoid println(FILE* f, format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file f
followed by a newline.
template <typename OutputIt, typename...\u00a0T>\nauto format_to(OutputIt&& out, format_string<T...> fmt, T&&... args) -\u2060>\u00a0remove_cvref_t<OutputIt>;
Formats args
according to specifications in fmt
, writes the result to the output iterator out
and returns the iterator past the end of the output range. format_to
does not append a terminating null character.
Example:
auto out = std::vector<char>();\nfmt::format_to(std::back_inserter(out), \"{}\", 42);\n
template <typename OutputIt, typename...\u00a0T>\nauto format_to_n(OutputIt out, size_t n, format_string<T...> fmt, T&&... args) -\u2060>\u00a0format_to_n_result<OutputIt>;
Formats args
according to specifications in fmt
, writes up to n
characters of the result to the output iterator out
and returns the total (not truncated) output size and the iterator past the end of the output range. format_to_n
does not append a terminating null character.
template <typename OutputIt>\nstruct format_to_n_result;
OutputIt out;
Iterator past the end of the output range.
size_t size;
Total (not truncated) output size.
template <typename...\u00a0T>\nauto formatted_size(format_string<T...> fmt, T&&... args) -\u2060>\u00a0size_t;
Returns the number of chars in the output of format(fmt, args...)
.
"},{"location":"api/#formatting-user-defined-types","title":"Formatting User-Defined Types","text":"
The {fmt} library provides formatters for many standard C++ types. See fmt/ranges.h
for ranges and tuples including standard containers such as std::vector
, fmt/chrono.h
for date and time formatting and fmt/std.h
for other standard library types.
There are two ways to make a user-defined type formattable: providing a format_as
function or specializing the formatter
struct template.
Use format_as
if you want to make your type formattable as some other type with the same format specifiers. The format_as
function should take an object of your type and return an object of a formattable type. It should be defined in the same namespace as your type.
Example (run):
#include <fmt/format.h>\n\nnamespace kevin_namespacy {\n\nenum class film {\n house_of_cards, american_beauty, se7en = 7\n};\n\nauto format_as(film f) { return fmt::underlying(f); }\n\n}\n\nint main() {\n fmt::print(\"{}\\n\", kevin_namespacy::film::se7en); // Output: 7\n}
Using specialization is more complex but gives you full control over parsing and formatting. To use this method specialize the formatter
struct template for your type and implement parse
and format
methods.
The recommended way of defining a formatter is by reusing an existing one via inheritance or composition. This way you can support standard format specifiers without implementing them yourself. For example:
// color.h:\n#include <fmt/base.h>\n\nenum class color {red, green, blue};\n\ntemplate <> struct fmt::formatter<color>: formatter<string_view> {\n // parse is inherited from formatter<string_view>.\n\n auto format(color c, format_context& ctx) const\n -> format_context::iterator;\n};\n
// color.cc:\n#include \"color.h\"\n#include <fmt/format.h>\n\nauto fmt::formatter<color>::format(color c, format_context& ctx) const\n -> format_context::iterator {\n string_view name = \"unknown\";\n switch (c) {\n case color::red: name = \"red\"; break;\n case color::green: name = \"green\"; break;\n case color::blue: name = \"blue\"; break;\n }\n return formatter<string_view>::format(name, ctx);\n}\n
Note that formatter<string_view>::format
is defined in fmt/format.h
so it has to be included in the source file. Since parse
is inherited from formatter<string_view>
it will recognize all string format specifications, for example
fmt::format(\"{:>10}\", color::blue)\n
will return \" blue\"
.
In general the formatter has the following form:
template <> struct fmt::formatter<T> {\n // Parses format specifiers and stores them in the formatter.\n //\n // [ctx.begin(), ctx.end()) is a, possibly empty, character range that\n // contains a part of the format string starting from the format\n // specifications to be parsed, e.g. in\n //\n // fmt::format(\"{:f} continued\", ...);\n //\n // the range will contain \"f} continued\". The formatter should parse\n // specifiers until '}' or the end of the range. In this example the\n // formatter should parse the 'f' specifier and return an iterator\n // pointing to '}'.\n constexpr auto parse(format_parse_context& ctx)\n -> format_parse_context::iterator;\n\n // Formats value using the parsed format specification stored in this\n // formatter and writes the output to ctx.out().\n auto format(const T& value, format_context& ctx) const\n -> format_context::iterator;\n};
It is recommended to at least support fill, align and width that apply to the whole object and have the same semantics as in standard formatters.
You can also write a formatter for a hierarchy of classes:
// demo.h:\n#include <type_traits>\n#include <fmt/core.h>\n\nstruct A {\n virtual ~A() {}\n virtual std::string name() const { return \"A\"; }\n};\n\nstruct B : A {\n virtual std::string name() const { return \"B\"; }\n};\n\ntemplate <typename T>\nstruct fmt::formatter<T, std::enable_if_t<std::is_base_of_v<A, T>, char>> :\n fmt::formatter<std::string> {\n auto format(const A& a, format_context& ctx) const {\n return formatter<std::string>::format(a.name(), ctx);\n }\n};\n
// demo.cc:\n#include \"demo.h\"\n#include <fmt/format.h>\n\nint main() {\n B b;\n A& a = b;\n fmt::print(\"{}\", a); // Output: B\n}\n
Providing both a formatter
specialization and a format_as
overload is disallowed.
template <typename Char>\nusing basic_format_parse_context = parse_context<Char>;
class context;
context(iterator out, format_args args, detail::locale_ref loc);
Constructs a context
object. References to the arguments are stored in the object so make sure they have appropriate lifetimes.
using format_context = context;
"},{"location":"api/#compile-time-checks","title":"Compile-Time Checks","text":"
Compile-time format string checks are enabled by default on compilers that support C++20 consteval
. On older compilers you can use the FMT_STRING macro defined in fmt/format.h
instead.
Unused arguments are allowed as in Python's str.format
and ordinary functions.
template <typename Char, typename...\u00a0T>\nusing basic_format_string = basic_fstring<Char, T...>;
template <typename...\u00a0T>\nusing format_string = typename fstring<T...>::t;
auto runtime(string_view s) -\u2060>\u00a0runtime_format_string<>;
Creates a runtime format string.
Example:
// Check format string at runtime instead of compile-time.\nfmt::print(fmt::runtime(\"{:d}\"), \"I am not a number\");\n
"},{"location":"api/#named-arguments","title":"Named Arguments","text":"
template <typename Char, typename T>\nauto arg(const Char* name, const T& arg) -\u2060>\u00a0detail::named_arg<Char, T>;
Returns a named argument to be used in a formatting function. It should only be used in a call to a formatting function.
Example:
fmt::print(\"The answer is {answer}.\", fmt::arg(\"answer\", 42));\n
Named arguments are not supported in compile-time checks at the moment.
"},{"location":"api/#type-erasure","title":"Type Erasure","text":"
You can create your own formatting function with compile-time checks and small binary footprint, for example (run):
#include <fmt/format.h>\n\nvoid vlog(const char* file, int line,\n fmt::string_view fmt, fmt::format_args args) {\n fmt::print(\"{}: {}: {}\", file, line, fmt::vformat(fmt, args));\n}\n\ntemplate <typename... T>\nvoid log(const char* file, int line,\n fmt::format_string<T...> fmt, T&&... args) {\n vlog(file, line, fmt, fmt::make_format_args(args...));\n}\n\n#define MY_LOG(fmt, ...) log(__FILE__, __LINE__, fmt, __VA_ARGS__)\n\nMY_LOG(\"invalid squishiness: {}\", 42);\n
Note that vlog
is not parameterized on argument types which improves compile times and reduces binary code size compared to a fully parameterized version.
template <typename Context, typename...\u00a0T, int\u00a0NUM_ARGS, int\u00a0NUM_NAMED_ARGS, unsigned long long\u00a0DESC>\nconstexpr auto make_format_args(T&... args) -\u2060>\u00a0detail::format_arg_store<Context, NUM_ARGS, NUM_NAMED_ARGS, DESC>;
Constructs an object that stores references to arguments and can be implicitly converted to format_args
. Context
can be omitted in which case it defaults to context
. See arg
for lifetime considerations.
template <typename Context>\nclass basic_format_args;
A view of a collection of formatting arguments. To avoid lifetime issues it should only be used as a parameter type in type-erased functions such as vformat
:
void vlog(fmt::string_view fmt, fmt::format_args args); // OK\nfmt::format_args args = fmt::make_format_args(); // Dangling reference\n
constexpr basic_format_args(const store<NUM_ARGS, NUM_NAMED_ARGS, DESC>& s);
Constructs a basic_format_args
object from format_arg_store
.
constexpr basic_format_args(const format_arg* args, int count, bool has_named);
Constructs a basic_format_args
object from a dynamic list of arguments.
auto get(int id) -\u2060>\u00a0format_arg;
Returns the argument with the specified id.
using format_args = basic_format_args<context>;
template <typename Context>\nclass basic_format_arg;
auto visit(Visitor&& vis) -\u2060>\u00a0decltype(vis(0));
Visits an argument dispatching to the appropriate visit method based on the argument type. For example, if the argument type is double
then vis(value)
will be called with the value of type double
.
"},{"location":"api/#compatibility","title":"Compatibility","text":"
template <typename Char>\nclass basic_string_view;
An implementation of std::basic_string_view
for pre-C++17. It provides a subset of the API. fmt::basic_string_view
is used for format strings even if std::basic_string_view
is available to prevent issues when a library is compiled with a different -std
option than the client code (which is not recommended).
constexpr basic_string_view(const Char* s, size_t count);
Constructs a string reference object from a C string and a size.
basic_string_view(const Char* s);
Constructs a string reference object from a C string.
basic_string_view(const S& s);
Constructs a string reference from a std::basic_string
or a std::basic_string_view
object.
constexpr auto data() -\u2060>\u00a0const Char*;
Returns a pointer to the string data.
constexpr auto size() -\u2060>\u00a0size_t;
Returns the string size.
using string_view = basic_string_view<char>;
"},{"location":"api/#format-api","title":"Format API","text":"
fmt/format.h
defines the full format API providing additional formatting functions and locale support.
template <typename...\u00a0T>\nauto format(format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::string;
Formats args
according to specifications in fmt
and returns the result as a string.
Example:
#include <fmt/format.h>\nstd::string message = fmt::format(\"The answer is {}.\", 42);\n
auto vformat(string_view fmt, format_args args) -\u2060>\u00a0std::string;
template <detail::fixed_string\u00a0Str>\nconstexpr auto operator\"\"_a();
"},{"location":"api/#utilities","title":"Utilities","text":"
template <typename T>\nauto ptr(T p) -\u2060>\u00a0const void*;
Converts p
to const void*
for pointer formatting.
Example:
auto s = fmt::format(\"{}\", fmt::ptr(p));\n
template <typename Enum>\nconstexpr auto underlying(Enum e) -\u2060>\u00a0underlying_t<Enum>;
Converts e
to the underlying type.
Example:
enum class color { red, green, blue };\nauto s = fmt::format(\"{}\", fmt::underlying(color::red));\n
template <typename T>\nauto to_string(const T& value) -\u2060>\u00a0std::string;
template <typename T>\nauto group_digits(T value) -\u2060>\u00a0group_digits_view<T>;
Returns a view that formats an integer value using ',' as a locale-independent thousands separator.
Example:
fmt::print(\"{}\", fmt::group_digits(12345));\n// Output: \"12,345\"\n
template <typename T>\nclass detail::buffer;
A contiguous memory buffer with an optional growing ability. It is an internal class and shouldn't be used directly, only via memory_buffer
.
constexpr auto size() -\u2060>\u00a0size_t;
Returns the size of this buffer.
constexpr auto capacity() -\u2060>\u00a0size_t;
Returns the capacity of this buffer.
auto data() -\u2060>\u00a0T*;
Returns a pointer to the buffer data (not null-terminated).
void clear();
Clears this buffer.
void append(const U* begin, const U* end);
Appends data to the end of the buffer.
template <typename T, size_t\u00a0SIZE, typename Allocator>\nclass basic_memory_buffer;
A dynamically growing memory buffer for trivially copyable/constructible types with the first SIZE
elements stored in the object itself. Most commonly used via the memory_buffer
alias for char
.
Example:
auto out = fmt::memory_buffer();\nfmt::format_to(std::back_inserter(out), \"The answer is {}.\", 42);\n
This will append \"The answer is 42.\" to out
. The buffer content can be converted to std::string
with to_string(out)
.
basic_memory_buffer(basic_memory_buffer&& other);
Constructs a basic_memory_buffer
object moving the content of the other object to it.
auto operator=(basic_memory_buffer&& other) -\u2060>\u00a0basic_memory_buffer&;
Moves the content of the other basic_memory_buffer
object to this one.
void resize(size_t count);
Resizes the buffer to contain count
elements. If T is a POD type new elements may not be initialized.
void reserve(size_t new_capacity);
Increases the buffer capacity to new_capacity
.
"},{"location":"api/#system-errors","title":"System Errors","text":"
{fmt} does not use errno
to communicate errors to the user, but it may call system functions which set errno
. Users should not make any assumptions about the value of errno
being preserved by library functions.
template <typename...\u00a0T>\nauto system_error(int error_code, format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::system_error;
Constructs std::system_error
with a message formatted with fmt::format(fmt, args...)
. error_code
is a system error code as given by errno
.
Example:
// This throws std::system_error with the description\n// cannot open file 'madeup': No such file or directory\n// or similar (system message may vary).\nconst char* filename = \"madeup\";\nFILE* file = fopen(filename, \"r\");\nif (!file)\n throw fmt::system_error(errno, \"cannot open file '{}'\", filename);\n
void format_system_error(detail::buffer<char>& out, int error_code, const char* message);
Formats an error message for an error returned by an operating system or a language runtime, for example a file opening error, and writes it to out
. The format is the same as the one used by std::system_error(ec, message)
where ec
is std::error_code(error_code, std::generic_category())
. It is implementation-defined but normally looks like:
<message>: <system-message>\n
where <message>
is the passed message and <system-message>
is the system message corresponding to the error code. error_code
is a system error code as given by errno
.
"},{"location":"api/#custom-allocators","title":"Custom Allocators","text":"
The {fmt} library supports custom dynamic memory allocators. A custom allocator class can be specified as a template argument to fmt::basic_memory_buffer
:
using custom_memory_buffer = \n fmt::basic_memory_buffer<char, fmt::inline_buffer_size, custom_allocator>;
It is also possible to write a formatting function that uses a custom allocator:
using custom_string =\n std::basic_string<char, std::char_traits<char>, custom_allocator>;\n\nauto vformat(custom_allocator alloc, fmt::string_view fmt,\n fmt::format_args args) -> custom_string {\n auto buf = custom_memory_buffer(alloc);\n fmt::vformat_to(std::back_inserter(buf), fmt, args);\n return custom_string(buf.data(), buf.size(), alloc);\n}\n\ntemplate <typename ...Args>\nauto format(custom_allocator alloc, fmt::string_view fmt,\n const Args& ... args) -> custom_string {\n return vformat(alloc, fmt, fmt::make_format_args(args...));\n}
The allocator will be used for the output container only. Formatting functions normally don't do any allocations for built-in and string types except for non-default floating-point formatting that occasionally falls back on sprintf
.
"},{"location":"api/#locale","title":"Locale","text":"
All formatting is locale-independent by default. Use the 'L'
format specifier to insert the appropriate number separator characters from the locale:
#include <fmt/core.h>\n#include <locale>\n\nstd::locale::global(std::locale(\"en_US.UTF-8\"));\nauto s = fmt::format(\"{:L}\", 1000000); // s == \"1,000,000\"
fmt/format.h
provides the following overloads of formatting functions that take std::locale
as a parameter. The locale type is a template parameter to avoid the expensive <locale>
include.
template <typename...\u00a0T>\nauto format(detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0std::string;
template <typename OutputIt, typename...\u00a0T>\nauto format_to(OutputIt out, detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0OutputIt;
template <typename...\u00a0T>\nauto formatted_size(detail::locale_ref loc, format_string<T...> fmt, T&&... args) -\u2060>\u00a0size_t;
"},{"location":"api/#legacy-compile-time-checks","title":"Legacy Compile-Time Checks","text":"
FMT_STRING
enables compile-time checks on older compilers. It requires C++14 or later and is a no-op in C++11.
FMT_STRING(s)
Constructs a compile-time format string from a string literal s
.
Example:
// A compile-time error because 'd' is an invalid specifier for strings.\nstd::string s = fmt::format(FMT_STRING(\"{:d}\"), \"foo\");\n
To force the use of legacy compile-time checks, define the preprocessor variable FMT_ENFORCE_COMPILE_STRING
. When set, functions accepting FMT_STRING
will fail to compile with regular strings.
"},{"location":"api/#range-and-tuple-formatting","title":"Range and Tuple Formatting","text":"
fmt/ranges.h
provides formatting support for ranges and tuples:
#include <fmt/ranges.h>\n\nfmt::print(\"{}\", std::tuple<char, int>{'a', 42});\n// Output: ('a', 42)
Using fmt::join
, you can separate tuple elements with a custom separator:
#include <fmt/ranges.h>\n\nauto t = std::tuple<int, char>{1, 'a'};\nfmt::print(\"{}\", fmt::join(t, \", \"));\n// Output: 1, a
template <typename Range>\nauto join(Range&& r, string_view sep) -\u2060>\u00a0join_view<decltype(detail::range_begin(r)), decltype(detail::range_end(r))>;
Returns a view that formats range
with elements separated by sep
.
Example:
auto v = std::vector<int>{1, 2, 3};\nfmt::print(\"{}\", fmt::join(v, \", \"));\n// Output: 1, 2, 3\n
fmt::join
applies passed format specifiers to the range elements:
fmt::print(\"{:02}\", fmt::join(v, \", \"));\n// Output: 01, 02, 03\n
template <typename It, typename Sentinel>\nauto join(It begin, Sentinel end, string_view sep) -\u2060>\u00a0join_view<It, Sentinel>;
Returns a view that formats the iterator range [begin, end)
with elements separated by sep
.
template <typename T>\nauto join(std::initializer_list<T> list, string_view sep) -\u2060>\u00a0join_view<const T*, const T*>;
Returns an object that formats std::initializer_list
with elements separated by sep
.
Example:
fmt::print(\"{}\", fmt::join({1, 2, 3}, \", \"));\n// Output: \"1, 2, 3\"\n
"},{"location":"api/#date-and-time-formatting","title":"Date and Time Formatting","text":"
fmt/chrono.h
provides formatters for
std::chrono::duration
std::chrono::time_point
std::tm
The format syntax is described in Chrono Format Specifications.
Example:
#include <fmt/chrono.h>\n\nint main() {\n std::time_t t = std::time(nullptr);\n\n fmt::print(\"The date is {:%Y-%m-%d}.\", fmt::localtime(t));\n // Output: The date is 2020-11-07.\n // (with 2020-11-07 replaced by the current date)\n\n using namespace std::literals::chrono_literals;\n\n fmt::print(\"Default format: {} {}\\n\", 42s, 100ms);\n // Output: Default format: 42s 100ms\n\n fmt::print(\"strftime-like format: {:%H:%M:%S}\\n\", 3h + 15min + 30s);\n // Output: strftime-like format: 03:15:30\n}
auto localtime(std::time_t time) -\u2060>\u00a0std::tm;
Converts given time since epoch as std::time_t
value into calendar time, expressed in local time. Unlike std::localtime
, this function is thread-safe on most platforms.
auto gmtime(std::time_t time) -\u2060>\u00a0std::tm;
Converts given time since epoch as std::time_t
value into calendar time, expressed in Coordinated Universal Time (UTC). Unlike std::gmtime
, this function is thread-safe on most platforms.
"},{"location":"api/#standard-library-types-formatting","title":"Standard Library Types Formatting","text":"
fmt/std.h
provides formatters for:
std::atomic
std::atomic_flag
std::bitset
std::error_code
std::exception
std::filesystem::path
std::monostate
std::optional
std::source_location
std::thread::id
std::variant
template <typename T, typename Deleter>\nauto ptr(const std::unique_ptr<T, Deleter>& p) -\u2060>\u00a0const void*;
template <typename T>\nauto ptr(const std::shared_ptr<T>& p) -\u2060>\u00a0const void*;
"},{"location":"api/#formatting-variants","title":"Formatting Variants","text":"
A std::variant
is only formattable if every variant alternative is formattable, and requires the __cpp_lib_variant
library feature.
Example:
#include <fmt/std.h>\n\nfmt::print(\"{}\", std::variant<char, float>('x'));\n// Output: variant('x')\n\nfmt::print(\"{}\", std::variant<std::monostate, char>());\n// Output: variant(monostate)
"},{"location":"api/#format-string-compilation","title":"Format String Compilation","text":"
fmt/compile.h
provides format string compilation enabled via the FMT_COMPILE
macro or the _cf
user-defined literal defined in namespace fmt::literals
. Format strings marked with FMT_COMPILE
or _cf
are parsed, checked and converted into efficient formatting code at compile-time. This supports arguments of built-in and string types as well as user-defined types with format
functions taking the format context type as a template parameter in their formatter
specializations. For example:
template <> struct fmt::formatter<point> {\n constexpr auto parse(format_parse_context& ctx);\n\n template <typename FormatContext>\n auto format(const point& p, FormatContext& ctx) const;\n};
Format string compilation can generate more binary code compared to the default API and is only recommended in places where formatting is a performance bottleneck.
FMT_COMPILE(s)
Converts a string literal s
into a format string that will be parsed at compile time and converted into efficient formatting code. Requires C++17 constexpr if
compiler support.
Example:
// Converts 42 into std::string using the most efficient method and no\n// runtime format string processing.\nstd::string s = fmt::format(FMT_COMPILE(\"{}\"), 42);\n
template <detail::fixed_string\u00a0Str>\nconstexpr auto operator\"\"_cf();
"},{"location":"api/#terminal-colors-and-text-styles","title":"Terminal Colors and Text Styles","text":"
fmt/color.h
provides support for terminal color and text style output.
template <typename...\u00a0T>\nvoid print(const text_style& ts, format_string<T...> fmt, T&&... args);
Formats a string and prints it to stdout using ANSI escape sequences to specify text formatting.
Example:
fmt::print(fmt::emphasis::bold | fg(fmt::color::red),\n \"Elapsed time: {0:.2f} seconds\", 1.23);\n
auto fg(detail::color_type foreground) -\u2060>\u00a0text_style;
Creates a text style from the foreground (text) color.
auto bg(detail::color_type background) -\u2060>\u00a0text_style;
Creates a text style from the background color.
template <typename T>\nauto styled(const T& value, text_style ts) -\u2060>\u00a0detail::styled_arg<remove_cvref_t<T>>;
Returns an argument that will be formatted using ANSI escape sequences, to be used in a formatting function.
Example:
fmt::print(\"Elapsed time: {0:.2f} seconds\",\n fmt::styled(1.23, fmt::fg(fmt::color::green) |\n fmt::bg(fmt::color::blue)));\n
"},{"location":"api/#system-apis","title":"System APIs","text":"
class ostream;
A fast buffered output stream for writing from a single thread. Writing from multiple threads without external synchronization may result in a data race.
void print(format_string<T...> fmt, T&&... args);
Formats args
according to specifications in fmt
and writes the output to the file.
template <typename...\u00a0T>\nauto windows_error(int error_code, string_view message, const T&... args) -\u2060>\u00a0std::system_error;
Constructs a std::system_error
object with the description of the form
<message>: <system-message>\n
where <message>
is the formatted message and <system-message>
is the system message corresponding to the error code. error_code
is a Windows error code as given by GetLastError
. If error_code
is not a valid error code such as -1, the system message will look like \"error -1\".
Example:
// This throws a system_error with the description\n// cannot open file 'madeup': The system cannot find the file\n
specified. // or similar (system message may vary). const char *filename = \"madeup\"; LPOFSTRUCT of = LPOFSTRUCT(); HFILE file = OpenFile(filename, &of, OF_READ); if (file == HFILE_ERROR) { throw fmt::windows_error(GetLastError(), \"cannot open file '{}'\", filename); }
"},{"location":"api/#stdostream-support","title":"
std::ostream
Support","text":"
fmt/ostream.h
provides std::ostream
support including formatting of user-defined types that have an overloaded insertion operator (operator<<
). In order to make a type formattable via std::ostream
you should provide a formatter
specialization inherited from ostream_formatter
:
#include <fmt/ostream.h>\n\nstruct date {\n int year, month, day;\n\n friend std::ostream& operator<<(std::ostream& os, const date& d) {\n return os << d.year << '-' << d.month << '-' << d.day;\n }\n};\n\ntemplate <> struct fmt::formatter<date> : ostream_formatter {};\n\nstd::string s = fmt::format(\"The date is {}\", date{2012, 12, 9});\n// s == \"The date is 2012-12-9\"
template <typename T>\nconstexpr auto streamed(const T& value) -\u2060>\u00a0detail::streamed_view<T>;
Returns a view that formats value
via an ostream operator<<
.
Example:
fmt::print(\"Current thread id: {}\\n\",\n fmt::streamed(std::this_thread::get_id()));\n
template <typename...\u00a0T>\nvoid print(std::ostream& os, format_string<T...> fmt, T&&... args);
Prints formatted data to the stream os
.
Example:
fmt::print(cerr, \"Don't {}!\", \"panic\");\n
"},{"location":"api/#dynamic-argument-lists","title":"Dynamic Argument Lists","text":"
The header fmt/args.h
provides dynamic_format_arg_store
, a builder-like API that can be used to construct format argument lists dynamically.
template <typename Context>\nclass dynamic_format_arg_store;
A dynamic list of formatting arguments with storage.
It can be implicitly converted into fmt::basic_format_args
for passing into type-erased formatting functions such as fmt::vformat
.
void push_back(const T& arg);
Adds an argument into the dynamic store for later passing to a formatting function.
Note that custom types and string types (but not string views) are copied into the store dynamically allocating memory if necessary.
Example:
fmt::dynamic_format_arg_store<fmt::format_context> store;\nstore.push_back(42);\nstore.push_back(\"abc\");\nstore.push_back(1.5f);\nstd::string result = fmt::vformat(\"{} and {} and {}\", store);\n
void push_back(std::reference_wrapper<T> arg);
Adds a reference to the argument into the dynamic store for later passing to a formatting function.
Example:
fmt::dynamic_format_arg_store<fmt::format_context> store;\nchar band[] = \"Rolling Stones\";\nstore.push_back(std::cref(band));\nband[9] = 'c'; // Changing str affects the output.\nstd::string result = fmt::vformat(\"{}\", store);\n// result == \"Rolling Scones\"\n
void push_back(const detail::named_arg<char_type, T>& arg);
Adds named argument into the dynamic store for later passing to a formatting function. std::reference_wrapper
is supported to avoid copying of the argument. The name is always copied into the store.
void clear();
Erase all elements from the store.
void reserve(size_t new_cap, size_t new_cap_named);
Reserves space to store at least new_cap
arguments including new_cap_named
named arguments.
"},{"location":"api/#safe-printf","title":"Safe
printf
","text":"
The header fmt/printf.h
provides printf
-like formatting functionality. The following functions use printf format string syntax with the POSIX extension for positional arguments. Unlike their standard counterparts, the fmt
functions are type-safe and throw an exception if an argument type doesn't match its format specification.
template <typename...\u00a0T>\nauto printf(string_view fmt, const T&... args) -\u2060>\u00a0int;
Formats args
according to specifications in fmt
and writes the output to stdout
.
Example:
fmt::printf(\"Elapsed time: %.2f seconds\", 1.23);
template <typename S, typename...\u00a0T, typename Char>\nauto fprintf(std::FILE* f, const S& fmt, const T&... args) -\u2060>\u00a0int;
Formats args
according to specifications in fmt
and writes the output to f
.
Example:
fmt::fprintf(stderr, \"Don't %s!\", \"panic\");\n
template <typename S, typename...\u00a0T, typename Char>\nauto sprintf(const S& fmt, const T&... args) -\u2060>\u00a0std::basic_string<Char>;
Formats args
according to specifications in fmt
and returns the result as as string.
Example:
std::string message = fmt::sprintf(\"The answer is %d\", 42);\n
"},{"location":"api/#wide-strings","title":"Wide Strings","text":"
The optional header fmt/xchar.h
provides support for wchar_t
and exotic character types.
template <typename T>\nstruct is_char;
using wstring_view = basic_string_view<wchar_t>;
using wformat_context = buffered_context<wchar_t>;
template <typename T>\nauto to_wstring(const T& value) -\u2060>\u00a0std::wstring;
Converts value
to std::wstring
using the default format for type T
.
"},{"location":"api/#compatibility-with-c20-stdformat","title":"Compatibility with C++20
std::format
","text":"
{fmt} implements nearly all of the C++20 formatting library with the following differences:
- Names are defined in the
fmt
namespace instead of std
to avoid collisions with standard library implementations. - Width calculation doesn't use grapheme clusterization. The latter has been implemented in a separate branch but hasn't been integrated yet.
"},{"location":"get-started/","title":"Get Started","text":"
Compile and run {fmt} examples online with Compiler Explorer.
{fmt} is compatible with any build system. The next section describes its usage with CMake, while the Build Systems section covers the rest.
"},{"location":"get-started/#cmake","title":"CMake","text":"
{fmt} provides two CMake targets: fmt::fmt
for the compiled library and fmt::fmt-header-only
for the header-only library. It is recommended to use the compiled library for improved build times.
There are three primary ways to use {fmt} with CMake:
-
FetchContent: Starting from CMake 3.11, you can use FetchContent
to automatically download {fmt} as a dependency at configure time:
include(FetchContent)\n\nFetchContent_Declare(\n fmt\n GIT_REPOSITORY https://github.com/fmtlib/fmt\n GIT_TAG e69e5f977d458f2650bb346dadf2ad30c5320281) # 10.2.1\nFetchContent_MakeAvailable(fmt)\n\ntarget_link_libraries(<your-target> fmt::fmt)
-
Installed: You can find and use an installed version of {fmt} in your CMakeLists.txt
file as follows:
find_package(fmt)\ntarget_link_libraries(<your-target> fmt::fmt)
-
Embedded: You can add the {fmt} source tree to your project and include it in your CMakeLists.txt
file:
add_subdirectory(fmt)\ntarget_link_libraries(<your-target> fmt::fmt)
"},{"location":"get-started/#installation","title":"Installation","text":""},{"location":"get-started/#debianubuntu","title":"Debian/Ubuntu","text":"
To install {fmt} on Debian, Ubuntu, or any other Debian-based Linux distribution, use the following command:
apt install libfmt-dev
"},{"location":"get-started/#homebrew","title":"Homebrew","text":"
Install {fmt} on macOS using Homebrew:
brew install fmt
"},{"location":"get-started/#conda","title":"Conda","text":"
Install {fmt} on Linux, macOS, and Windows with Conda, using its conda-forge package:
conda install -c conda-forge fmt
"},{"location":"get-started/#vcpkg","title":"vcpkg","text":"
Download and install {fmt} using the vcpkg package manager:
git clone https://github.com/Microsoft/vcpkg.git\ncd vcpkg\n./bootstrap-vcpkg.sh\n./vcpkg integrate install\n./vcpkg install fmt
"},{"location":"get-started/#building-from-source","title":"Building from Source","text":"
CMake works by generating native makefiles or project files that can be used in the compiler environment of your choice. The typical workflow starts with:
mkdir build # Create a directory to hold the build output.\ncd build\ncmake .. # Generate native build scripts.
run in the fmt
repository.
If you are on a Unix-like system, you should now see a Makefile in the current directory. Now you can build the library by running make
.
Once the library has been built you can invoke make test
to run the tests.
You can control generation of the make test
target with the FMT_TEST
CMake option. This can be useful if you include fmt as a subdirectory in your project but don't want to add fmt's tests to your test
target.
To build a shared library set the BUILD_SHARED_LIBS
CMake variable to TRUE
:
cmake -DBUILD_SHARED_LIBS=TRUE ..
To build a static library with position-independent code (e.g. for linking it into another shared library such as a Python extension), set the CMAKE_POSITION_INDEPENDENT_CODE
CMake variable to TRUE
:
cmake -DCMAKE_POSITION_INDEPENDENT_CODE=TRUE ..
After building the library you can install it on a Unix-like system by running sudo make install
.
"},{"location":"get-started/#building-the-docs","title":"Building the Docs","text":"
To build the documentation you need the following software installed on your system:
- Python
- Doxygen
- MkDocs with
mkdocs-material
, mkdocstrings
, pymdown-extensions
and mike
First generate makefiles or project files using CMake as described in the previous section. Then compile the doc
target/project, for example:
make doc
This will generate the HTML documentation in doc/html
.
"},{"location":"get-started/#build-systems","title":"Build Systems","text":""},{"location":"get-started/#build2","title":"build2","text":"
You can use build2, a dependency manager and a build system, to use {fmt}.
Currently this package is available in these package repositories:
- https://cppget.org/fmt/ for released and published versions.
- https://github.com/build2-packaging/fmt for unreleased or custom versions.
Usage:
build2
package name: fmt
- Library target name:
lib{fmt}
To make your build2
project depend on fmt
:
-
Add one of the repositories to your configurations, or in your repositories.manifest
, if not already there:
:\nrole: prerequisite\nlocation: https://pkg.cppget.org/1/stable
-
Add this package as a dependency to your manifest
file (example for version 10):
depends: fmt ~10.0.0
-
Import the target and use it as a prerequisite to your own target using fmt
in the appropriate buildfile
:
import fmt = fmt%lib{fmt}\nlib{mylib} : cxx{**} ... $fmt
Then build your project as usual with b
or bdep update
.
"},{"location":"get-started/#meson","title":"Meson","text":"
Meson WrapDB includes an fmt
package.
Usage:
- Install the
fmt
subproject from the WrapDB by running:meson wrap install fmt
from the root of your project.
-
In your project's meson.build
file, add an entry for the new subproject:
fmt = subproject('fmt')\nfmt_dep = fmt.get_variable('fmt_dep')
-
Include the new dependency object to link with fmt:
my_build_target = executable(\n 'name', 'src/main.cc', dependencies: [fmt_dep])
Options:
If desired, {fmt} can be built as a static library, or as a header-only library.
For a static build, use the following subproject definition:
fmt = subproject('fmt', default_options: 'default_library=static')\nfmt_dep = fmt.get_variable('fmt_dep')
For the header-only version, use:
fmt = subproject('fmt')\nfmt_dep = fmt.get_variable('fmt_header_only_dep')
"},{"location":"get-started/#android-ndk","title":"Android NDK","text":"
{fmt} provides Android.mk file that can be used to build the library with Android NDK.
"},{"location":"get-started/#other","title":"Other","text":"
To use the {fmt} library with any other build system, add include/fmt/base.h
, include/fmt/format.h
, include/fmt/format-inl.h
, src/format.cc
and optionally other headers from a release archive or the git repository to your project, add include
to include directories and make sure src/format.cc
is compiled and linked with your code.
"},{"location":"syntax/","title":"Format String Syntax","text":"
Formatting functions such as fmt::format
and fmt::print
use the same format string syntax described in this section.
Format strings contain \"replacement fields\" surrounded by curly braces {}
. Anything that is not contained in braces is considered literal text, which is copied unchanged to the output. If you need to include a brace character in the literal text, it can be escaped by doubling: {{
and }}
.
The grammar for a replacement field is as follows:
replacement_field ::= \"{\" [arg_id] [\":\" (format_spec | chrono_format_spec)] \"}\"\narg_id ::= integer | identifier\ninteger ::= digit+\ndigit ::= \"0\"...\"9\"\nidentifier ::= id_start id_continue*\nid_start ::= \"a\"...\"z\" | \"A\"...\"Z\" | \"_\"\nid_continue ::= id_start | digit
\n
In less formal terms, the replacement field can start with an arg_id that specifies the argument whose value is to be formatted and inserted into the output instead of the replacement field. The arg_id is optionally followed by a format_spec, which is preceded by a colon ':'
. These specify a non-default format for the replacement value.
See also the Format Specification Mini-Language section.
If the numerical arg_ids in a format string are 0, 1, 2, ... in sequence, they can all be omitted (not just some) and the numbers 0, 1, 2, ... will be automatically inserted in that order.
Named arguments can be referred to by their names or indices.
Some simple format string examples:
\"First, thou shalt count to {0}\" // References the first argument\n\"Bring me a {}\" // Implicitly references the first argument\n\"From {} to {}\" // Same as \"From {0} to {1}\"\n
The format_spec field contains a specification of how the value should be presented, including such details as field width, alignment, padding, decimal precision and so on. Each value type can define its own \"formatting mini-language\" or interpretation of the format_spec.
Most built-in types support a common formatting mini-language, which is described in the next section.
A format_spec field can also include nested replacement fields in certain positions within it. These nested replacement fields can contain only an argument id; format specifications are not allowed. This allows the formatting of a value to be dynamically specified.
See the Format Examples section for some examples.
"},{"location":"syntax/#format-specification-mini-language","title":"Format Specification Mini-Language","text":"
\"Format specifications\" are used within replacement fields contained within a format string to define how individual values are presented. Each formattable type may define how the format specification is to be interpreted.
Most built-in types implement the following options for format specifications, although some of the formatting options are only supported by the numeric types.
The general form of a standard format specifier is:
format_spec ::= [[fill]align][sign][\"#\"][\"0\"][width][\".\" precision][\"L\"][type]\nfill ::= <a character other than '{' or '}'>\nalign ::= \"<\" | \">\" | \"^\"\nsign ::= \"+\" | \"-\" | \" \"\nwidth ::= integer | \"{\" [arg_id] \"}\"\nprecision ::= integer | \"{\" [arg_id] \"}\"\ntype ::= \"a\" | \"A\" | \"b\" | \"B\" | \"c\" | \"d\" | \"e\" | \"E\" | \"f\" | \"F\" |\n \"g\" | \"G\" | \"o\" | \"p\" | \"s\" | \"x\" | \"X\" | \"?\"
\n
The fill character can be any Unicode code point other than '{'
or '}'
. The presence of a fill character is signaled by the character following it, which must be one of the alignment options. If the second character of format_spec is not a valid alignment option, then it is assumed that both the fill character and the alignment option are absent.
The meaning of the various alignment options is as follows:
Option Meaning
'<'
Forces the field to be left-aligned within the available space (this is the default for most objects).
'>'
Forces the field to be right-aligned within the available space (this is the default for numbers).
'^'
Forces the field to be centered within the available space.
Note that unless a minimum field width is defined, the field width will always be the same size as the data to fill it, so that the alignment option has no meaning in this case.
The sign option is only valid for floating point and signed integer types, and can be one of the following:
Option Meaning
'+'
Indicates that a sign should be used for both nonnegative as well as negative numbers.
'-'
Indicates that a sign should be used only for negative numbers (this is the default behavior). space Indicates that a leading space should be used on nonnegative numbers, and a minus sign on negative numbers.
The '#'
option causes the \"alternate form\" to be used for the conversion. The alternate form is defined differently for different types. This option is only valid for integer and floating-point types. For integers, when binary, octal, or hexadecimal output is used, this option adds the prefix respective \"0b\"
(\"0B\"
), \"0\"
, or \"0x\"
(\"0X\"
) to the output value. Whether the prefix is lower-case or upper-case is determined by the case of the type specifier, for example, the prefix \"0x\"
is used for the type 'x'
and \"0X\"
is used for 'X'
. For floating-point numbers the alternate form causes the result of the conversion to always contain a decimal-point character, even if no digits follow it. Normally, a decimal-point character appears in the result of these conversions only if a digit follows it. In addition, for 'g'
and 'G'
conversions, trailing zeros are not removed from the result.
width is a decimal integer defining the minimum field width. If not specified, then the field width will be determined by the content.
Preceding the width field by a zero ('0'
) character enables sign-aware zero-padding for numeric types. It forces the padding to be placed after the sign or base (if any) but before the digits. This is used for printing fields in the form \"+000000120\". This option is only valid for numeric types and it has no effect on formatting of infinity and NaN. This option is ignored when any alignment specifier is present.
The precision is a decimal number indicating how many digits should be displayed after the decimal point for a floating-point value formatted with 'f'
and 'F'
, or before and after the decimal point for a floating-point value formatted with 'g'
or 'G'
. For non-number types the field indicates the maximum field size - in other words, how many characters will be used from the field content. The precision is not allowed for integer, character, Boolean, and pointer values. Note that a C string must be null-terminated even if precision is specified.
The 'L'
option uses the current locale setting to insert the appropriate number separator characters. This option is only valid for numeric types.
Finally, the type determines how the data should be presented.
The available string presentation types are:
Type Meaning
's'
String format. This is the default type for strings and may be omitted.
'?'
Debug format. The string is quoted and special characters escaped. none The same as
's'
.
The available character presentation types are:
Type Meaning
'c'
Character format. This is the default type for characters and may be omitted.
'?'
Debug format. The character is quoted and special characters escaped. none The same as
'c'
.
The available integer presentation types are:
Type Meaning
'b'
Binary format. Outputs the number in base 2. Using the
'#'
option with this type adds the prefix
\"0b\"
to the output value.
'B'
Binary format. Outputs the number in base 2. Using the
'#'
option with this type adds the prefix
\"0B\"
to the output value.
'c'
Character format. Outputs the number as a character.
'd'
Decimal integer. Outputs the number in base 10.
'o'
Octal format. Outputs the number in base 8.
'x'
Hex format. Outputs the number in base 16, using lower-case letters for the digits above 9. Using the
'#'
option with this type adds the prefix
\"0x\"
to the output value.
'X'
Hex format. Outputs the number in base 16, using upper-case letters for the digits above 9. Using the
'#'
option with this type adds the prefix
\"0X\"
to the output value. none The same as
'd'
.
Integer presentation types can also be used with character and Boolean values with the only exception that 'c'
cannot be used with bool
. Boolean values are formatted using textual representation, either true
or false
, if the presentation type is not specified.
The available presentation types for floating-point values are:
Type Meaning
'a'
Hexadecimal floating point format. Prints the number in base 16 with prefix
\"0x\"
and lower-case letters for digits above 9. Uses
'p'
to indicate the exponent.
'A'
Same as
'a'
except it uses upper-case letters for the prefix, digits above 9 and to indicate the exponent.
'e'
Exponent notation. Prints the number in scientific notation using the letter 'e' to indicate the exponent.
'E'
Exponent notation. Same as
'e'
except it uses an upper-case
'E'
as the separator character.
'f'
Fixed point. Displays the number as a fixed-point number.
'F'
Fixed point. Same as
'f'
, but converts
nan
to
NAN
and
inf
to
INF
.
'g'
General format. For a given precision p >= 1
, this rounds the number to p
significant digits and then formats the result in either fixed-point format or in scientific notation, depending on its magnitude.
A precision of 0
is treated as equivalent to a precision of 1
.
'G'
General format. Same as
'g'
except switches to
'E'
if the number gets too large. The representations of infinity and NaN are uppercased, too. none Similar to
'g'
, except that the default precision is as high as needed to represent the particular value.
The available presentation types for pointers are:
Type Meaning
'p'
Pointer format. This is the default type for pointers and may be omitted. none The same as
'p'
."},{"location":"syntax/#chrono-format-specifications","title":"Chrono Format Specifications","text":"
Format specifications for chrono duration and time point types as well as std::tm
have the following syntax:
chrono_format_spec ::= [[fill]align][width][\".\" precision][chrono_specs]\nchrono_specs ::= conversion_spec |\n chrono_specs (conversion_spec | literal_char)\nconversion_spec ::= \"%\" [padding_modifier] [locale_modifier] chrono_type\nliteral_char ::= <a character other than '{', '}' or '%'>\npadding_modifier ::= \"-\" | \"_\" | \"0\"\nlocale_modifier ::= \"E\" | \"O\"\nchrono_type ::= \"a\" | \"A\" | \"b\" | \"B\" | \"c\" | \"C\" | \"d\" | \"D\" | \"e\" |\n \"F\" | \"g\" | \"G\" | \"h\" | \"H\" | \"I\" | \"j\" | \"m\" | \"M\" |\n \"n\" | \"p\" | \"q\" | \"Q\" | \"r\" | \"R\" | \"S\" | \"t\" | \"T\" |\n \"u\" | \"U\" | \"V\" | \"w\" | \"W\" | \"x\" | \"X\" | \"y\" | \"Y\" |\n \"z\" | \"Z\" | \"%\"
\n
Literal chars are copied unchanged to the output. Precision is valid only for std::chrono::duration
types with a floating-point representation type.
The available presentation types (chrono_type) are:
Type Meaning
'a'
The abbreviated weekday name, e.g. \"Sat\". If the value does not contain a valid weekday, an exception of type
format_error
is thrown.
'A'
The full weekday name, e.g. \"Saturday\". If the value does not contain a valid weekday, an exception of type
format_error
is thrown.
'b'
The abbreviated month name, e.g. \"Nov\". If the value does not contain a valid month, an exception of type
format_error
is thrown.
'B'
The full month name, e.g. \"November\". If the value does not contain a valid month, an exception of type
format_error
is thrown.
'c'
The date and time representation, e.g. \"Sat Nov 12 22:04:00 1955\". The modified command
%Ec
produces the locale's alternate date and time representation.
'C'
The year divided by 100 using floored division, e.g. \"19\". If the result is a single decimal digit, it is prefixed with 0. The modified command
%EC
produces the locale's alternative representation of the century.
'd'
The day of month as a decimal number. If the result is a single decimal digit, it is prefixed with 0. The modified command
%Od
produces the locale's alternative representation.
'D'
Equivalent to
%m/%d/%y
, e.g. \"11/12/55\".
'e'
The day of month as a decimal number. If the result is a single decimal digit, it is prefixed with a space. The modified command
%Oe
produces the locale's alternative representation.
'F'
Equivalent to
%Y-%m-%d
, e.g. \"1955-11-12\".
'g'
The last two decimal digits of the ISO week-based year. If the result is a single digit it is prefixed by 0.
'G'
The ISO week-based year as a decimal number. If the result is less than four digits it is left-padded with 0 to four digits.
'h'
Equivalent to
%b
, e.g. \"Nov\".
'H'
The hour (24-hour clock) as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OH
produces the locale's alternative representation.
'I'
The hour (12-hour clock) as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OI
produces the locale's alternative representation.
'j'
If the type being formatted is a specialization of duration, the decimal number of days without padding. Otherwise, the day of the year as a decimal number. Jan 1 is 001. If the result is less than three digits, it is left-padded with 0 to three digits.
'm'
The month as a decimal number. Jan is 01. If the result is a single digit, it is prefixed with 0. The modified command
%Om
produces the locale's alternative representation.
'M'
The minute as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OM
produces the locale's alternative representation.
'n'
A new-line character.
'p'
The AM/PM designations associated with a 12-hour clock.
'q'
The duration's unit suffix.
'Q'
The duration's numeric value (as if extracted via
.count()
).
'r'
The 12-hour clock time, e.g. \"10:04:00 PM\".
'R'
Equivalent to
%H:%M
, e.g. \"22:04\".
'S'
Seconds as a decimal number. If the number of seconds is less than 10, the result is prefixed with 0. If the precision of the input cannot be exactly represented with seconds, then the format is a decimal floating-point number with a fixed format and a precision matching that of the precision of the input (or to a microseconds precision if the conversion to floating-point decimal seconds cannot be made within 18 fractional digits). The modified command
%OS
produces the locale's alternative representation.
't'
A horizontal-tab character.
'T'
Equivalent to
%H:%M:%S
.
'u'
The ISO weekday as a decimal number (1-7), where Monday is 1. The modified command
%Ou
produces the locale's alternative representation.
'U'
The week number of the year as a decimal number. The first Sunday of the year is the first day of week 01. Days of the same year prior to that are in week 00. If the result is a single digit, it is prefixed with 0. The modified command
%OU
produces the locale's alternative representation.
'V'
The ISO week-based week number as a decimal number. If the result is a single digit, it is prefixed with 0. The modified command
%OV
produces the locale's alternative representation.
'w'
The weekday as a decimal number (0-6), where Sunday is 0. The modified command
%Ow
produces the locale's alternative representation.
'W'
The week number of the year as a decimal number. The first Monday of the year is the first day of week 01. Days of the same year prior to that are in week 00. If the result is a single digit, it is prefixed with 0. The modified command
%OW
produces the locale's alternative representation.
'x'
The date representation, e.g. \"11/12/55\". The modified command
%Ex
produces the locale's alternate date representation.
'X'
The time representation, e.g. \"10:04:00\". The modified command
%EX
produces the locale's alternate time representation.
'y'
The last two decimal digits of the year. If the result is a single digit it is prefixed by 0. The modified command
%Oy
produces the locale's alternative representation. The modified command
%Ey
produces the locale's alternative representation of offset from
%EC
(year only).
'Y'
The year as a decimal number. If the result is less than four digits it is left-padded with 0 to four digits. The modified command
%EY
produces the locale's alternative full year representation.
'z'
The offset from UTC in the ISO 8601:2004 format. For example -0430 refers to 4 hours 30 minutes behind UTC. If the offset is zero, +0000 is used. The modified commands
%Ez
and
%Oz
insert a
:
between the hours and minutes: -04:30. If the offset information is not available, an exception of type
format_error
is thrown.
'Z'
The time zone abbreviation. If the time zone abbreviation is not available, an exception of type
format_error
is thrown.
'%'
A % character.
Specifiers that have a calendaric component such as 'd'
(the day of month) are valid only for std::tm
and time points but not durations.
The available padding modifiers (padding_modifier) are:
Type Meaning
'-'
Pad a numeric result with spaces.
'_'
Do not pad a numeric result string.
'0'
Pad a numeric result string with zeros.
These modifiers are only supported for the 'H'
, 'I'
, 'M'
, 'S'
, 'U'
, 'V'
, 'W'
, 'm'
, 'j'
, 'Y'
presentation types.
"},{"location":"syntax/#range-format-specifications","title":"Range Format Specifications","text":"
Format specifications for range types have the following syntax:
range_format_spec ::= [\"n\"][range_type][range_underlying_spec]
\n
The 'n'
option formats the range without the opening and closing brackets.
The available presentation types for range_type
are:
Type Meaning none Default format.
's'
String format. The range is formatted as a string.
'?\u2060s'
Debug format. The range is formatted as an escaped string.
If range_type
is 's'
or '?s'
, the range element type must be a character type. The 'n'
option and range_underlying_spec
are mutually exclusive with 's'
and '?s'
.
The range_underlying_spec
is parsed based on the formatter of the range's element type.
By default, a range of characters or strings is printed escaped and quoted. But if any range_underlying_spec
is provided (even if it is empty), then the characters or strings are printed according to the provided specification.
Examples:
fmt::print(\"{}\", std::vector{10, 20, 30});\n// Output: [10, 20, 30]\nfmt::print(\"{::#x}\", std::vector{10, 20, 30});\n// Output: [0xa, 0x14, 0x1e]\nfmt::print(\"{}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: ['h', 'e', 'l', 'l', 'o']\nfmt::print(\"{:n}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: 'h', 'e', 'l', 'l', 'o'\nfmt::print(\"{:s}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: \"hello\"\nfmt::print(\"{:?s}\", std::vector{'h', 'e', 'l', 'l', 'o', '\\n'});\n// Output: \"hello\\n\"\nfmt::print(\"{::}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: [h, e, l, l, o]\nfmt::print(\"{::d}\", std::vector{'h', 'e', 'l', 'l', 'o'});\n// Output: [104, 101, 108, 108, 111]\n
"},{"location":"syntax/#format-examples","title":"Format Examples","text":"
This section contains examples of the format syntax and comparison with the printf formatting.
In most of the cases the syntax is similar to the printf formatting, with the addition of the {}
and with :
used instead of %
. For example, \"%03.2f\"
can be translated to \"{:03.2f}\"
.
The new format syntax also supports new and different options, shown in the following examples.
Accessing arguments by position:
fmt::format(\"{0}, {1}, {2}\", 'a', 'b', 'c');\n// Result: \"a, b, c\"\nfmt::format(\"{}, {}, {}\", 'a', 'b', 'c');\n// Result: \"a, b, c\"\nfmt::format(\"{2}, {1}, {0}\", 'a', 'b', 'c');\n// Result: \"c, b, a\"\nfmt::format(\"{0}{1}{0}\", \"abra\", \"cad\"); // arguments' indices can be repeated\n// Result: \"abracadabra\"\n
Aligning the text and specifying a width:
fmt::format(\"{:<30}\", \"left aligned\");\n// Result: \"left aligned \"\nfmt::format(\"{:>30}\", \"right aligned\");\n// Result: \" right aligned\"\nfmt::format(\"{:^30}\", \"centered\");\n// Result: \" centered \"\nfmt::format(\"{:*^30}\", \"centered\"); // use '*' as a fill char\n// Result: \"***********centered***********\"\n
Dynamic width:
fmt::format(\"{:<{}}\", \"left aligned\", 30);\n// Result: \"left aligned \"\n
Dynamic precision:
fmt::format(\"{:.{}f}\", 3.14, 1);\n// Result: \"3.1\"\n
Replacing %+f
, %-f
, and % f
and specifying a sign:
fmt::format(\"{:+f}; {:+f}\", 3.14, -3.14); // show it always\n// Result: \"+3.140000; -3.140000\"\nfmt::format(\"{: f}; {: f}\", 3.14, -3.14); // show a space for positive numbers\n// Result: \" 3.140000; -3.140000\"\nfmt::format(\"{:-f}; {:-f}\", 3.14, -3.14); // show only the minus -- same as '{:f}; {:f}'\n// Result: \"3.140000; -3.140000\"\n
Replacing %x
and %o
and converting the value to different bases:
fmt::format(\"int: {0:d}; hex: {0:x}; oct: {0:o}; bin: {0:b}\", 42);\n// Result: \"int: 42; hex: 2a; oct: 52; bin: 101010\"\n// with 0x or 0 or 0b as prefix:\nfmt::format(\"int: {0:d}; hex: {0:#x}; oct: {0:#o}; bin: {0:#b}\", 42);\n// Result: \"int: 42; hex: 0x2a; oct: 052; bin: 0b101010\"\n
Padded hex byte with prefix and always prints both hex characters:
fmt::format(\"{:#04x}\", 0);\n// Result: \"0x00\"\n
Box drawing using Unicode fill:
fmt::print(\n \"\u250c{0:\u2500^{2}}\u2510\\n\"\n \"\u2502{1: ^{2}}\u2502\\n\"\n \"\u2514{0:\u2500^{2}}\u2518\\n\", \"\", \"Hello, world!\", 20);\n
prints:
\u250c\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510\n\u2502 Hello, world! \u2502\n\u2514\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2518\n
Using type-specific formatting:
#include <fmt/chrono.h>\n\nauto t = tm();\nt.tm_year = 2010 - 1900;\nt.tm_mon = 7;\nt.tm_mday = 4;\nt.tm_hour = 12;\nt.tm_min = 15;\nt.tm_sec = 58;\nfmt::print(\"{:%Y-%m-%d %H:%M:%S}\", t);\n// Prints: 2010-08-04 12:15:58\n
Using the comma as a thousands separator:
#include <fmt/format.h>\n\nauto s = fmt::format(std::locale(\"en_US.UTF-8\"), \"{:L}\", 1234567890);\n// s == \"1,234,567,890\"\n
"}]}
\ No newline at end of file
diff --git a/dev/sitemap.xml.gz b/dev/sitemap.xml.gz
index 606733849003756b51c292f707c7cccbc5356172..5e1ccf0aa28168323f211ae281c256c28d4b89e7 100644
GIT binary patch
delta 13
Ucmb=gXP58h;AqHJoycAR02?*~-~a#s
delta 13
Ucmb=gXP58h;9!tanaExN02ZAC4gdfE