admin管理员组文章数量:1356104
How can I create a format string using std functions (not the external fmt library), where the format arguments are contained within a std::vector<std::string>
.
Something like the following (but this example version doesn't compile):
std::string format(std::string fmt, const std::vector<std::string>& list) {
return std::vformat(fmt, std::make_format_args(list.begin(), list.end()));
}
How can I create a format string using std functions (not the external fmt library), where the format arguments are contained within a std::vector<std::string>
.
Something like the following (but this example version doesn't compile):
std::string format(std::string fmt, const std::vector<std::string>& list) {
return std::vformat(fmt, std::make_format_args(list.begin(), list.end()));
}
Share
Improve this question
edited Mar 30 at 23:43
David G
96.9k41 gold badges172 silver badges258 bronze badges
asked Mar 30 at 23:28
DessDess
2,68727 silver badges41 bronze badges
3
- The library is no longer external as of C++20. – PaulMcKenzie Commented Mar 30 at 23:53
- @PaulMcKenzie: I'm talking about the actual 'fmt' external library, not the C++ format facilities. I obviously showed that in the example code. – Dess Commented Mar 30 at 23:58
- You can't. If you can at least change to a container with compile-time size, you can do something like this: godbolt./z/earGYsWvT – Intelligent Shade of Blue Commented Mar 31 at 0:58
1 Answer
Reset to default 0I don't think what you are attempting is possible with standard formatting functions. std::format()
and friends utilize template parameter packs for their input arguments, and parameter packs can only be constructed at compile-time, not dynamically at runtime.
To do what you want, you will need to manually pull apart the fmt
string into replacement and non-replacement substrings, and then build up the output std::string
concatenation those substrings, making replacements as needed.
For example, if you have a fmt
string "{} {} my name is {}"
and a vector {"Hello", "World", "Dess"}
, then you would extract the following substrings and then concatenate them together:
"{}"
-> "Hello"
" "
"{}"
-> "World"
" my name is "
"{}"
-> "Dess"
However, note that prior to C++26, std::format()
requires a string literal for its fmt
parameter. So you can't use std::format()
in this case. C++26 will introduce std::runtime_format
so you can pass in a std::string
/std::string_view
constructed at runtime, but in the meantime, you will have to use std::vformat()
and std::make_format_args()
with single-argument replacements.
Try something like this:
std::string format(const std::string_view &fmt, const std::vector<std::string>& list) {
std::string result;
std::string::size_type start = 0, pos, end;
std::vector<std::string>::size_type idx = 0;
while ((pos = fmt.find('{', start)) != std::string::npos) {
if (pos > start) result += fmt.substr(start, pos-start);
if ((end = fmt.find('}', pos+1)) == std::string::npos) break;
++end;
result += std::vformat(fmt.substr(pos, end-pos), std::make_format_args(list.at(idx++)));
start = end;
}
if (start < fmt.size()) result += fmt.substr(start);
return result;
}
Live Demo
Obviously, you'll have to make this more robust to support the full syntax that the fmt
parameter supports, but this should give you an idea to start with.
本文标签: cMake formatted string with arguments in string vectorStack Overflow
版权声明:本文标题:c++ - Make formatted string with arguments in string vector - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1743972240a2570736.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论