3

我想将我自己的对象输出到 STL 流,但具有自定义格式。我想出了这样的东西,但是因为我从来没有使用过语言环境和灌输,所以我不知道这是否有意义以及如何实现 MyFacet 和 operator<<。

所以我的问题是:这是否有意义以及如何实现 MyFacet 和 operator<< ?

以下是一个简化的示例,它向您展示了我想要做什么。

struct MyObject
{
  int i;
  std::string s;
};

std::ostream &operator<<(std::ostream &os, const MyObject &obj)
{
    if (????)
    {
        os << obj.i;
    }
    else
    {
        os << obj.s;
    }
}

MyObject o;
o.i = 1;
o.s = "hello";

std::cout.imbue(locale("", new MyFacet(MyFacet::UseInt)));
std::cout << o << std::endl;    // prints "1"

std::cout.imbue(locale("", new MyFacet(MyFacet::UseString)));
std::cout << o << std::endl;    // prints "hello"
4

2 回答 2

4

实现您自己的操作符 << 进行跟踪通常是一个好主意。但是,我从来不需要灌输语言环境。不过我试过了,效果很好。这是我所做的:

class my_facet : public std::locale::facet
{
public:
    enum option{
        use_string,
        use_numeric
    };
    //Unique id for facet family, no locale can contain two
    //facets with same id.
    static std::locale::id id; 
    my_facet(option o=use_numeric):
    facet(0),
        _option(o)
    {//Initialize reference count to zero so that the memory
     //management will be handled by locale
    };
    option get_option() const {return _option;};
protected:
    option _option;
};
std::locale::id my_facet::id(123456); //Facet family unique id

std::ostream& operator<<(std::ostream& os, const myobj& o)
{
    std::locale const& l = os.getloc();
    if( std::has_facet<my_facet>(l) ){
        my_facet const& f =  std::use_facet<my_facet>(l);
        switch(f.get_option()){
        case my_facet::use_numeric:
            os << "Using numeric! ";
            break;
        case my_facet::use_string:
            os << "Using string! ";
            break;
        default:
            os << "Unhandled case.. ";
            break;
        }
        return os;
    }
    os << "Default case when no facet has been set";
    return os;
}

然后用这个方面灌输一个语言环境:

std::locale mylocale(locale("US"), new my_facet(my_facet::use_numeric));
std::cout.imbue(mylocale);

然而,更优雅的方法是实现可以在语言环境中替换的同一方面系列的不同方面。

于 2009-07-08T07:12:38.890 回答
1

好吧,语言环境通常用于允许基于存在的本地(实际上是指定的语言环境)格式对同一对象进行不同的输出/输入格式。有关这方面的好文章,请参见: http: //www.cantrip.org/locale.html。现在可能是因为您上面的示例非常简化,但对我来说,您似乎正在尝试想出一种聪明的方法来在打印对象的一部分或另一部分之间进行切换。如果是这种情况,可能会更简单,只需为每种类型重载流运算符并在外部使用 if 开关。

无论如何,我不会假装我是方面和语言环境方面的专家,但请看一下那篇文章,它非常透彻,会给你比我更好的解释!

于 2009-07-08T06:15:07.710 回答