`
zuroc
  • 浏览: 1309752 次
  • 性别: Icon_minigender_1
  • 来自: 江苏
社区版块
存档分类
最新评论

C++ std名字空间ostream_iterator与的诡异问题

    博客分类:
  • C++
阅读更多
为了方便显示map而自定义的两个函数,出现了一个诡异的问题,感谢jinq0123@163.com告之解决方法,但是我对问题的原因还是不太清楚.

这里的Blog好像有问题,我把<该为了《........................

cpp 代码
 
  1. #include 《map》  
  2. #include 《string》  
  3. #include 《iterator》  
  4. #include 《iostream》  
  5.   
  6. using namespace std;  
  7. namespace std     
  8. {     
  9.      //如果不将该函数放入名字空间std则使用ostream_iterator不能通过编译  
  10.      //但是可以直接用cout输出pair  
  11.   
  12.     templateclass _Elem,class _Traits,class K,class V》  
  13.     basic_ostream《_Elem,_Traits》& operator《《(  
  14.         basic_ostream《_Elem,_Traits》& s  
  15.         ,  
  16.         const pair《K,V》& p  
  17.         )  
  18.     {  
  19.         return s《《p.first《《" : "《《p.second;  
  20.     }  
  21.   
  22. }  
  23.   
  24. templateclass _Elem,class _Traits,class K,class V》  
  25. basic_ostream《_Elem,_Traits》&  operator《《(  
  26.     basic_ostream《_Elem,_Traits》& s  
  27.     ,   
  28.     const map《K,V》& m  
  29. )  
  30. {  
  31.     copy(m.begin(), m.end(), ostream_iterator《pair《K,V》 》(s, "\n"));  
  32.     return s;  
  33. }  
  34.   
  35. int main()  
  36. {  
  37.     using namespace std;  
  38.     map《string,string》 a;  
  39.     a["key1"]="value1";  
  40.     a["key2"]="value2";  
  41.     cout《《a;  
  42.     system("pause");  
  43.     return 0;  
  44. }  
分享到:
评论
3 楼 zuroc 2007-05-15  

> using namespace std;
> namespace std
> {
>        //If don't put this function into namespace std , there will be
> a
> compile error .

>        template<class _Elem,class _Traits,class K,class V>
>        basic_ostream<_Elem,_Traits>& operator<<(
>                basic_ostream<_Elem,_Traits>& s
>                ,
>                const pair<K,V>& p
>                )
>        {
>                return s<<p.first<<" : "<<p.second;
>        }

> }

> template<class _Elem,class _Traits,class K,class V>
> basic_ostream<_Elem,_Traits>&  operator<<(
>        basic_ostream<_Elem,_Traits>& s
>        ,
>        const map<K,V>& m
> )
> {
>        copy(m.begin(), m.end(), ostream_iterator<pair<K,V> >(s,
> "\n"));
>        return s;

> }

> int main()
> {
>        using namespace std;
>        map<string,string> a;
>        a["key1"]="value1";
>        a["key2"]="value2";
>        cout<<a;
>        system("pause");
>        return 0;

> }

We had a similar discussion some time ago.
Please read http://tinyurl.com/yvca6w for the
details (If this link does not lead to the correct
entry, please read contribution 14).

The short version is: Don't do that! You are not
allowed to add such an overload to namespace
std which brings you in the realm of undefined
behaviour. The above quoted thread shows in
contribution 14 that there are at least two clean
solutions:

1) Change your operator template overload by a corresponding function template (e.g. "print") in your user namespace. Then replace your std::copy invocation by a std::for_each call (which uses a special print functor and *not* operator<< on std::pair) or use an explicit loop.

2) Use a better customizable iterator like boost::transform_iterator which uses the print-functor mentioned in (1).

Greetings from Bremen,

Daniel Krügler
2 楼 shifan3 2007-05-15  
因为otream_iterator的定义在std里,所以它首先会在std里查找operator》,只要找到一个名字一样的(尽管可能参数不一样),就不会继续到global namespace里查找了
这个确实是标准规定的
1 楼 Elminster 2007-05-10  
名称查找的问题吧 …… 可能是类模板中对引用名字做两段式查找的时候按照类模板定义点来了,不太确定这个行为是否符合标准。

转去 www.cpper.com/c/ 问这个问题吧。

相关推荐

    C++迭代器介绍(iterator、const_iterator、reverse_interator、const_reverse_interator)

    它们通常用于向输出流(如文件或`std::ostream`)写入数据,例如`std::ostream_iterator`。 3. **向前迭代器(Forward Iterator)**:在输入迭代器的基础上,向前迭代器还支持前向移动多次,但仍然不支持后退。例如...

    c++使用stl进行系列化和反系列化.docx

    在这个例子中,我们使用了`std::vector`、`std::ifstream`、`std::ofstream`、`std::istream_iterator`、`std::ostream_iterator`以及`std::back_inserter`等STL组件。 1. **序列化到文件**: 序列化是将数据结构...

    ostream用法解释

    C++中的ostream类是输入/输出流库中一个非常重要的组件,它提供了一种灵活的方式来处理输入/输出操作。在本文中,我们将对ostream类的使用方法进行详细的解释,并提供实践示例。 ostream_iterator是流迭代器,属于...

    fstream.pdf

    为了实现文件数据的自动读取并存储到容器中,可以使用 `std::istream_iterator` 和 `std::ostream_iterator`。 下面是一个使用 `stream_iterator` 和 `fstream` 读取二进制文件的例子: ```cpp struct Opcode { ...

    c++程序设计(刘振安)程序举例[文].pdf

    例 1.6 展示了C++标准库中的算法,如`std::copy`、`std::reverse_copy`、`std::sort`以及`std::ostream_iterator`。`std::copy`用于复制数组,`std::reverse_copy`用于反向复制,`std::sort`对数组进行排序,`std::...

    泛型编程(C++)

    std::ostream_iterator(std::cout, "\n")); e.insert(--e.end(), TodaysDate()); std::copy(first, last, std::ostream_iterator(std::cout, "\n")); } ``` ##### 错误1:迭代器的有效性检查 - **问题描述**...

    The Standard Template Library

    STL定义了一系列迭代器标记,包括但不限于`std::input_iterator_tag`、`std::output_iterator_tag`、`std::forward_iterator_tag`、`std::bidirectional_iterator_tag`和`std::random_access_iterator_tag`。...

    KWIC问题C++版

    在C++中,管道风格通常涉及使用标准库中的`std::transform`、`std::istringstream`和`std::ostream_iterator`等工具。首先,我们将读取输入文本,然后通过一系列函数或操作符将文本分解成单词,接着按照KWIC格式...

    c++学习笔记w版.pdf

    `std::sort`函数用于对序列进行排序,`std::ostream_iterator`和`std::istream_iterator`则方便地实现了输入输出流与元素之间的转换。在实际编程中,这些工具可以组合使用,如读取输入,对数据排序,去重,然后写入...

    VC++入门经典(part2)

    输出流迭代器 (`ostream_iterator&lt;T&gt;`) 与输入流迭代器类似,但它用于将容器中的数据输出到流中。构造函数同样接受指向流的指针作为参数,通常为 `std::cout` 或其他输出流对象。 **示例代码**: ```cpp #include ...

    The C++ Standard Library(简体中文)

    - **迭代器之配接器(Iterator Adapters)**:这部分介绍了迭代器配接器,包括插入迭代器(`std::insert_iterator`)、串流迭代器(`std::istream_iterator`、`std::ostream_iterator`)和逆向迭代器(`std::reverse_...

    c++ boost asio http get post请求

    std::ostream request_stream(&request); request_stream ; request_stream ; request_stream ; request_stream &lt;&lt; "Content-Length: " &lt;&lt; std::dec ; request_stream ; request_stream ; request_stream ;...

    C++标准模板库函数

    - **输出迭代器(Output Iterator)**:只能写入元素,不能读取,如ostream_iterator。 - **前向迭代器(Forward Iterator)**:具有输入迭代器的功能,并能向前遍历多次,如list::iterator。 - **双向迭代器...

    C++ Standard Library Practical Tips.doc

    结合`std::copy`和`std::ostream_iterator`。 ### `std::vector`技巧 #### TIP 17: 预留空间 使用`reserve()`避免不必要的内存重新分配。 #### TIP 18: 删除多余内存 使用`shrink_to_fit()`减少内存占用。 #### ...

    c++学习笔记w版.docx

    最后,迭代器还可以用于流式操作,例如`std::ostream_iterator`和`std::istream_iterator`,它们分别用于输出流和输入流。这使得在输入输出过程中,可以方便地读写元素序列。 总之,C++的学习涉及多个层面,包括...

    stl学习总结

    std::ostream_iterator&lt;int&gt; out_it(std::cout, " "); for (auto i : vector1) { *out_it = i; // 输出vector中的元素 ++out_it; } ``` ##### 输入迭代器(Input Iterator) 输入迭代器支持解引用操作`*first`来...

    数据结构 模板与迭代器

    通过`std::iterator_traits`,我们可以轻松地获取迭代器的相关信息,并基于这些信息来编写更加通用和高效的代码。 #### 总结 本文介绍了C++中模板和迭代器的基本概念及其应用。模板为程序员提供了一种编写通用代码...

    C++中读取控制台输出,并将文件指针FILE*转换为istream

    `FILE*`是C语言的标准I/O库中的类型,而C++的I/O操作则基于`std::iostream`库,它提供了`std::istream`和`std::ostream`等类。本篇文章将详细介绍如何在C++中读取控制台输出,并将`FILE*`转换为`istream`以便进行...

    C++ string 用法详解 - BYVoid1

    - `std::copy()`函数用于将去重后的元素复制到`std::ostream_iterator`,这会将结果输出到控制台。 6. **错误处理**: - 在示例代码中,没有显示错误处理部分。在实际应用中,应当对文件打开失败、读取异常等情况...

    通过代码实例解析c++ vector常用方法

    std::copy(x.begin(), x.end(), std::ostream_iterator(std::cout, " ")); ``` 这将打印`x`的元素,每个元素之间用空格分隔。 5. **获取vector中最大值和最小值及其索引**: 要找到`std::vector&lt;int&gt;`中的最大...

Global site tag (gtag.js) - Google Analytics