谁是对的,谁是错的又名GCC vs Visual Studio

时间:2011-02-26 11:27:56

标签: c++ visual-studio-2010 visual-c++ gcc

此代码(不能“正常”工作)但在VS 2010中编译但不会在GCC 4.5.1中编译

#include <iostream>
#include <vector>//not necessary second > should skip like brackets

using namespace std;

template<class ForwardIterator>
void iterator_swap(ForwardIterator& left,ForwardIterator& right)
{
    typename ForwardIterator::value_type tmp = *left;
    *left = *right;
    *right = tmp;
}

template<class T>
std::ostream& operator<<(std::ostream& out, const std::vector<T>& obj)
{
   typename std::vector<T>::const_iterator beg = obj.cbegin();
   typename std::vector<T>::const_iterator end = obj.cend();
    while (beg != end)
    {
        out << *beg << '\n';
        ++beg;
    }
    return out;
}

int main()
{
    vector<unsigned> v_1;
    for (vector<unsigned>::size_type i = 0; i < 10; ++i)
    {
        v_1.push_back(i);
    }
    vector<unsigned> v_2;
    for (vector<unsigned>::size_type i = 0; i < 10; ++i)
    {
        v_2.push_back(i*10);
    }
    cout << "v_1:\n" << v_1;
    cout << "v_2:\n" << v_2;
    iterator_swap(v_1.begin(),v_2.begin());
    cout << "After swap:\n";
    cout << "v_1:\n" << v_1;
    cout << "v_2:\n" << v_2;
    return 0;
}

在GCC中,我正在关注错误信息:

E:\CodeBlocks\Iter_swap\main.cpp|41|error: 
     invalid initialization of non-const reference of type     
       '__gnu_cxx::__normal_iterator<unsigned int*, std::vector<unsigned int, 
           std::allocator<unsigned int> > >&' from a temporary of type 
       '__gnu_cxx::__normal_iterator<unsigned int*, std::vector<unsigned int, 
           std::allocator<unsigned int> > >'|

那么哪支球队是对的? VS或GCC?

1 个答案:

答案 0 :(得分:13)

问题在于:

iterator_swap(v_1.begin(),v_2.begin());

您将临时(从begin()函数返回)传递给接受两个非const引用的函数。标准C ++禁止临时绑定到非const引用。 (但是,标准C ++允许临时绑定绑定到 const 引用。)

根据标准C ++,您无法将临时对象绑定到非const引用的GCC and VC++ (versions 2005 and later) "knows"。所以他们本身都是“正确的”。但是,Visual C ++实现了一个非标准扩展,允许临时代码以您在代码片段中的方式绑定到非const引用。

要抓住这样的内容,我强烈建议您使用level 4 warnings enabled (/W4) and treat warnings as errors (/WX) on Visual C++编译代码。它会捕获这些错误。