rapidyaml  0.13.0
parse and emit YAML, and do it fast
format: formatted string interpolation

Functions

template<class Arg , class... Args>
size_t c4::format (substr buf, csubstr fmt, Arg const &a, Args const &...more)
 Using a format string, serialize the arguments into the given fixed-size buffer. More...
 
template<class... Args>
substr c4::format_sub (substr buf, csubstr fmt, Args const &...args)
 like c4::format() but return a substr instead of a size More...
 
template<class CharOwningContainer , class... Args>
void c4::formatrs (CharOwningContainer *cont, csubstr fmt, Args const &...args)
 format+resize: like c4::format(), but receives a container, and resizes it as needed to contain the result. More...
 
template<class CharOwningContainer , class... Args>
CharOwningContainer c4::formatrs (csubstr fmt, Args const &...args)
 format+resize: like c4::format(), but create a new container with the result. More...
 
template<class CharOwningContainer , class... Args>
csubstr c4::formatrs_append (CharOwningContainer *cont, csubstr fmt, Args const &...args)
 format+resize+append: like c4::format(), but receives a container, and appends the arguments, resizing the container as needed to contain the result. More...
 

Detailed Description

Function Documentation

◆ format()

template<class Arg , class... Args>
size_t c4::format ( substr  buf,
csubstr  fmt,
Arg const &  a,
Args const &...  more 
)

Using a format string, serialize the arguments into the given fixed-size buffer.

The buffer size is strictly respected: no writes will occur beyond its end. In the format string, each argument is marked with a compact curly-bracket pair "{}". This pair does not take any interior sequence numbers or extra formatting arguments inside it (contrary to eg the C++20 std::format implementation or the Python formatting facilities). To enable argument customization, use the formatting facilities in Format specifiers wrapping the arguments passed to this function.

Returns
the number of bytes needed to write into the buffer.
See also
c4::formatrs() if instead of a fixed-size buffer, a resizeable container is desired
c4::unformat() for the inverse function
c4::cat() if no format or separator is needed
c4::catsep() if no format is needed, but a separator must be used

For example:

c4::format(buf, "the {} drank {} {}", "partier", 5, "beers"); // the partier drank 5 beers
c4::format(buf, "the {} drank {} {}", "programmer", 6, "coffees"); // the programmer drank 6 coffees
size_t format(substr buf, csubstr fmt, Arg const &a, Args const &...more)
Using a format string, serialize the arguments into the given fixed-size buffer.
Definition: format.hpp:940

Using Format specifiers enables control of the result. For example:

c4::format(buf, "the {} drank {} {}", "partier", c4::fmt::real(5, 3), "beers"); // the partier drank 5.000 beers
c4::format(buf, "the {} drank {} {}", "partier", c4::fmt::zpad(5, 3), "beers"); // the partier drank 005 beers
c4::format(buf, "the {} drank {} {}", "partier", c4::fmt::bin(5), "beers"); // the partier drank 0b101 beers
c4::format(buf, "the {} drank {} {}", "partier", c4::fmt::oct(5), "beers"); // the partier drank 0o6 beers
c4::format(buf, "the {} drank {} {}", "partier", c4::fmt::hex(5), "beers"); // the partier drank 0x6 beers
c4::format(buf, "the {} drank {} {}", "programmer", c4::fmt::real(6, 3), "coffees"); // the programmer drank 6.000 coffees
c4::format(buf, "the {} drank {} {}", "programmer", c4::fmt::zpad(6, 3), "coffees"); // the programmer drank 006 coffees
c4::format(buf, "the {} drank {} {}", "programmer", c4::fmt::bin(6), "coffees"); // the programmer drank 0b110 coffees
c4::format(buf, "the {} drank {} {}", "programmer", c4::fmt::oct(6), "coffees"); // the programmer drank 0o6 coffees
c4::format(buf, "the {} drank {} {}", "programmer", c4::fmt::hex(6), "coffees"); // the programmer drank 0x6 coffees
integral_< intptr_t > hex(std::nullptr_t)
format null as an hexadecimal value
Definition: format.hpp:160
integral_< intptr_t > bin(std::nullptr_t)
format null as a binary 0-1 value
Definition: format.hpp:212
integral_< intptr_t > oct(std::nullptr_t)
format null as an octal value
Definition: format.hpp:185
real_< T > real(T val, int precision, RealFormat_e fmt=FTOA_FLOAT)
Definition: format.hpp:366
integral_padded_< T > zpad(T val, size_t num_digits)
pad the argument with zeroes on the left, with decimal radix
Definition: format.hpp:232
Note
Arguments beyond the last curly bracket pair are silently ignored. Curly bracket pairs without a corresponding argument are printed as part of the result.
// note "and nothing else" being ignored
c4::format(buf, "the {} drank {} {}", "partier", 5, "beers", "and nothing else"); // the partier drank 5 beers
// note "this is ignored {}" being part of the result
c4::format(buf, "the {} drank {} {} this is ignored: {}", "programmer", 6, "coffees"); // the programmer drank 6 coffees this is ignored: {}
The curly bracket pair cannot be escaped, but can of course be placed into the result by passing an "{}" argument in its place, or if it is provided beyond the last argument passed to the function (see prior note).
// as above: no argument given, so no substitution made:
c4::format(buf, "let's show {} on the result"); // let's show {} on the result
// or just pass "{}" as an argument to force the substitution:
c4::format(buf, "let's show {} on the result and then {}", "{}", "this"); // let's show {} on the result and then this
The arguments to format are restricted (legal because they are rvalues). This may require a workaround when arguments of type char[]/const char[] are passed repeatedly to the function. For example,
const char str[] = "Hi! ";
cat(buf, str, str, str); // compile error: 'passing argument 2 to ‘restrict’-qualified parameter aliases with arguments 3, 4'
size_t cat(substr buf, Arg const &a, Args const &...more)
serialize the arguments, concatenating them to the given fixed-size buffer.
Definition: format.hpp:653
It is possible to work around the problem by suppressing -Wrestrict or by using the decayed type char* or const char*, or even wrapping the argument in a csubstr():
const char str[] = "Hi! ";
csubstr ss = to_csubstr(str);
cat(buf, ss, ss, ss); // ok! compiles cleanly
csubstr to_csubstr(substr s) noexcept
neutral version for use in generic code
Definition: substr.hpp:2204

Definition at line 940 of file format.hpp.

941 {
942  size_t pos = fmt.find("{}");
943  if(C4_UNLIKELY(pos == csubstr::npos))
944  return to_chars(buf, fmt);
945  size_t num = to_chars(buf, fmt.first(pos));
946  size_t out = num;
947  buf = buf.len >= num ? buf.sub(num) : substr{};
948  num = to_chars(buf, a);
949  out += num;
950  buf = buf.len >= num ? buf.sub(num) : substr{};
951  num = format(buf, fmt.sub(pos + 2), more...);
952  out += num;
953  return out;
954 }
size_t to_chars(substr buf, fmt::center_< T > const &align)
Definition: format.hpp:596
@ npos
a null string position
Definition: common.hpp:258

◆ format_sub()

template<class... Args>
substr c4::format_sub ( substr  buf,
csubstr  fmt,
Args const &...  args 
)

like c4::format() but return a substr instead of a size

See also
c4::format()
c4::catsep(). c4::uncatsep() is the inverse of c4::catsep().

Definition at line 960 of file format.hpp.

961 {
962  size_t sz = c4::format(buf, fmt, args...);
963  C4_CHECK(sz <= buf.len);
964  return {buf.str, sz <= buf.len ? sz : buf.len};
965 }

◆ formatrs() [1/2]

template<class CharOwningContainer , class... Args>
void c4::formatrs ( CharOwningContainer *  cont,
csubstr  fmt,
Args const &...  args 
)
inline

format+resize: like c4::format(), but receives a container, and resizes it as needed to contain the result.

The container is overwritten. To append to the container use c4::formatrs_append().

See also
c4::format()
c4::formatrs_append()
Note
The arguments to format are restricted (legal because they are rvalues). This may require a workaround when arguments of type char[]/const char[] are passed repeatedly to the function. For example,
const char str[] = "Hi! ";
cat(buf, str, str, str); // compile error: 'passing argument 2 to ‘restrict’-qualified parameter aliases with arguments 3, 4'
It is possible to work around the problem by suppressing -Wrestrict or by using the decayed type char* or const char*, or even wrapping the argument in a csubstr():
const char str[] = "Hi! ";
csubstr ss = to_csubstr(str);
cat(buf, ss, ss, ss); // ok! compiles cleanly

Definition at line 1267 of file format.hpp.

1268 {
1269  cont->resize(cont->capacity()); // improve the odds of fitting in the original buffer
1270 retry:
1271  substr buf = to_substr(*cont);
1272  size_t ret = format(buf, fmt, args...);
1273  cont->resize(ret);
1274  if(ret > buf.len)
1275  goto retry;
1276 }
substr to_substr(substr s) noexcept
neutral version for use in generic code
Definition: substr.hpp:2202

◆ formatrs() [2/2]

template<class CharOwningContainer , class... Args>
CharOwningContainer c4::formatrs ( csubstr  fmt,
Args const &...  args 
)
inline

format+resize: like c4::format(), but create a new container with the result.

Returns
the requested container
Note
The arguments to format are restricted (legal because they are rvalues). This may require a workaround when arguments of type char[]/const char[] are passed repeatedly to the function. For example,
const char str[] = "Hi! ";
cat(buf, str, str, str); // compile error: 'passing argument 2 to ‘restrict’-qualified parameter aliases with arguments 3, 4'
It is possible to work around the problem by suppressing -Wrestrict or by using the decayed type char* or const char*, or even wrapping the argument in a csubstr():
const char str[] = "Hi! ";
csubstr ss = to_csubstr(str);
cat(buf, ss, ss, ss); // ok! compiles cleanly

Definition at line 1302 of file format.hpp.

1303 {
1304  CharOwningContainer cont;
1305  formatrs(&cont, fmt, args...);
1306  return cont;
1307 }
CharOwningContainer formatrs(csubstr fmt, Args const &...args)
format+resize: like c4::format(), but create a new container with the result.
Definition: format.hpp:1302

◆ formatrs_append()

template<class CharOwningContainer , class... Args>
csubstr c4::formatrs_append ( CharOwningContainer *  cont,
csubstr  fmt,
Args const &...  args 
)
inline

format+resize+append: like c4::format(), but receives a container, and appends the arguments, resizing the container as needed to contain the result.

The buffer is appended to.

Returns
the region newly appended to the original container
Note
The arguments to format are restricted (legal because they are rvalues). This may require a workaround when arguments of type char[]/const char[] are passed repeatedly to the function. For example,
const char str[] = "Hi! ";
cat(buf, str, str, str); // compile error: 'passing argument 2 to ‘restrict’-qualified parameter aliases with arguments 3, 4'
It is possible to work around the problem by suppressing -Wrestrict or by using the decayed type char* or const char*, or even wrapping the argument in a csubstr():
const char str[] = "Hi! ";
csubstr ss = to_csubstr(str);
cat(buf, ss, ss, ss); // ok! compiles cleanly

Definition at line 1334 of file format.hpp.

1335 {
1336  const size_t pos = cont->size();
1337  cont->resize(cont->capacity()); // improve the odds of fitting in the original buffer
1338 retry:
1339  substr buf = to_substr(*cont).sub(pos);
1340  size_t ret = format(buf, fmt, args...);
1341  cont->resize(pos + ret);
1342  if(ret > buf.len)
1343  goto retry;
1344  return to_csubstr(*cont).range(pos, cont->size());
1345 }