マニピュレータの使用方法を制御できないため、C++ストリームにマニピュレータを追加することは特に困難です。ストリームに新しいロケールを組み込むことができます。ストリームには、数値の印刷方法を制御するファセットがインストールされていますが、文字列の出力方法は制御されていません。そして、問題は、引用状態をストリームに安全に保存する方法です。
std
文字列は、名前空間で定義された演算子を使用して出力されます。マニピュレータの外観を維持しながら、それらの印刷方法を変更したい場合は、プロキシクラスを作成できます。
namespace quoting {
struct quoting_proxy {
explicit quoting_proxy(std::ostream & os):os(os){}
template<typename Rhs>
friend std::ostream & operator<<(quoting_proxy const& q,
Rhs const& rhs) {
return q.os << rhs;
}
friend std::ostream & operator<<(quoting_proxy const& q,
std::string const& rhs) {
return q.os << "'" << rhs << "'";
}
friend std::ostream & operator<<(quoting_proxy const& q,
char const* rhs) {
return q.os << "'" << rhs << "'";
}
private:
std::ostream & os;
};
struct quoting_creator { } quote;
quoting_proxy operator<<(std::ostream & os, quoting_creator) {
return quoting_proxy(os);
}
}
int main() {
std::cout << quoting::quote << "hello" << std::endl;
}
に使用するのに適していますostream
。一般化したい場合は、それをテンプレートにしてbasic_stream
、プレーンの代わりに受け入れることもできstring
ます。場合によっては、標準のマニピュレータとは動作が異なります。プロキシオブジェクトを返すことで機能するため、次のような場合には機能しません
std::cout << quoting::quote;
std::cout << "hello";