简体   繁体   English

为什么在反向STL实施中需要交换? 加速的C ++(问题8.4)

[英]Why do we need swap in reverse STL implementation? Accelerated C++ (ques 8.4)

I am trying to answer the question: Why did we call swap rather than exchange the values of *first and *last in the implementation of reverse function? 我正在尝试回答这个问题:为什么在执行反向功能时我们调用交换而不是交换*first*last的值? Here is the reverse function: 这是反向功能:

template <class BiDirectionalIterator>
void reverse(BiDirectionalIterator first, BiDirectionalIterator last)
{
    while(first < last) {
        --last;
        if(first != last) {
            swap(*first++, *last);
        }
    }
}

I am trying to clear my understanding here. 我想在这里清除我的理解。 I tried exchanging *first and *last directly: 我尝试直接交换*first*last

template <class Bi>
void incorrect_reverse(Bi first, Bi last)
{
    while(first < last) {
        --last;
        if(first != last) {
            //here tmp and first both point to the same thing
            Bi tmp = first;
            *first = *last;
            *last = *tmp;
            first++;
        }
    }
}

I saw that this did not work. 我看到这没有用。 Then I tried Bi tmp = *first to get the value of first but get a compiler error. 然后我试图Bi tmp = *first得到的价值 first ,但得到一个编译错误。 Is there not way than calling the swap function that I can do this? 除了调用swap函数,没有其他方法可以做到这一点吗? I am looking for way to do it in the function itself. 我正在寻找在函数本身中执行此操作的方法。

You need to store the value *first as your temporary storage, not the iterator first . 您需要将值*first存储为临时存储,而不是迭代器first

auto tmp = *first;
*first = *last;
*last = tmp;
first++;

Otherwise you are overwriting *first without storing its previous value, and so you are essentially just copying from *last to *first (and then redundantly copying it back again), instead of swapping. 否则,您将覆盖*first而不存储其先前的值,因此从本质上来说,您只是从*last复制到*first (然后再冗余地复制回它),而不是交换。

The reason you got an error when you did this: 执行此操作时出现错误的原因:

Bi tmp = *first

Is because Bi is the type of the iterator, not the type of the value you are trying to swap. 是因为Bi是迭代器的类型,而不是您尝试交换的值的类型。 To get the correct type, you can just use auto like I did above, or you can be more explicit: 要获得正确的类型,您可以像上面一样使用auto ,或者可以更明确地使用:

typename std::iterator_traits<Bi>::value_type tmp = *first;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM