引数のセットを渡してstd::string
をフォーマットすることは可能ですか?
現在、文字列を次のようにフォーマットしています。
string helloString = "Hello %s and %s";
vector<string> tokens; //initialized vector of strings
const char* helloStringArr = helloString.c_str();
char output[1000];
sprintf_s(output, 1000, helloStringArr, tokens.at(0).c_str(), tokens.at(1).c_str());
ただし、ベクトルのサイズは実行時に決定されます。引数のコレクションを取り、std :: string/char *をフォーマットするsprintf_s
に類似した関数はありますか?私の開発環境はMSVisual C++ 2010Expressです。
編集:私は似たようなことを達成したいと思います:
sprintf_s(output, 1000, helloStringArr, tokens);
Boost.Format ライブラリを使用してこれを行うことができます。これは、引数を1つずつフィードできるためです。
これにより、すべての引数を一度に渡す必要があるprintf
ファミリとはまったく異なり、実際に目標を達成できます(つまり、コンテナ内の各アイテムに手動でアクセスする必要があります)。
例:
#include <boost/format.hpp>
#include <string>
#include <vector>
#include <iostream>
std::string format_range(const std::string& format_string, const std::vector<std::string>& args)
{
boost::format f(format_string);
for (std::vector<std::string>::const_iterator it = args.begin(); it != args.end(); ++it) {
f % *it;
}
return f.str();
}
int main()
{
std::string helloString = "Hello %s and %s";
std::vector<std::string> args;
args.Push_back("Alice");
args.Push_back("Bob");
std::cout << format_range(helloString, args) << '\n';
}
ここから作業したり、テンプレート化したりできます。
ベクトルに正確な量の引数が含まれていない場合は、例外(ドキュメントを参照)がスローされることに注意してください。それらの処理方法を決定する必要があります。
Sprintfのような機能を実現するための最もC++風の方法は、 stringstreams を使用することです。
コードに基づく例を次に示します。
#include <sstream>
// ...
std::stringstream ss;
std::vector<std::string> tokens;
ss << "Hello " << tokens.at(0) << " and " << tokens.at(1);
std::cout << ss.str() << std::endl;
かなり便利ですね。
もちろん、さまざまなsprintfフラグを置き換えるIOStream操作の利点を最大限に活用できます。参照については、ここ http://www.fredosaurus.com/notes-cpp/io/omanipulators.html を参照してください。
より完全な例:
#include <string>
#include <sstream>
#include <iostream>
#include <iomanip>
int main() {
std::stringstream s;
s << "coucou " << std::setw(12) << 21 << " test";
std::cout << s.str() << std::endl;
return 0;
}
印刷するもの:
coucou 21 test
編集:
OPが指摘しているように、この方法では可変個引数引数を使用できません。これは、ストリームがベクトルを反復処理し、プレースホルダーに従ってデータを挿入できるようにする事前に作成された「テンプレート」文字列がないためです。
boost :: format ライブラリは、出力バッファを手動で処理する必要がないようにする場合に役立ちます。
プレーンベクトルを入力として使用する場合、tokens.size()<2
の場合はどうなりますか?いずれにせよ、ベクトルが要素0と1にインデックスを付けるのに十分な大きさであることを確認する必要はありませんか?