簡體   English   中英

使用reverse_iterator反轉數組(向量)

[英]Reversing an array (vector) using reverse_iterator

我正在嘗試使用Edabit挑戰並測試“新”功能來提高我的c ++知識。 當前的挑戰是希望我們編寫一個函數來反轉數組。 例子:

reverse([1, 2, 3, 4]) ➞ [4, 3, 2, 1]

reverse([9, 9, 2, 3, 4]) ➞ [4, 3, 2, 9, 9]

reverse([]) ➞ []

我嘗試使用reverse_iterator進行此操作,但結果有些奇怪。

std::vector<int> reverse(std::vector<int> arr) {
    std::vector<int> out;
    for(std::vector<int>::reverse_iterator i = arr.rbegin(); i != arr.rend(); ++i)
    {
        out.push_back(arr[*i]);
    }
    return out;
}

我得到的結果如下:

FAILED: Expected: equal to [ 4, 3, 2, 1 ]
Actual: [ 0, 4, 3, 2 ]

首先,看起來好像只有一次,o我在rbegin()中加了1並撕成如下:

for(std::vector<int>::reverse_iterator i = arr.rbegin() + 1; i != arr.rend() + 1; ++i)

似乎第一個測試通過了,但是隨后的測試似乎還很遙遠:

FAILED: Expected: equal to [ 7, 6, 5 ]
Actual: [ 33, 0, 5 ]

我正在嘗試了解此反向迭代器的工作方式,因此請提供解決方案,並提供一些清晰的解釋,說明為什么第一個測試加上1才通過,第二個為什么沒有通過。

嘗試:

for(std::vector<int>::reverse_iterator i = arr.rbegin(); i != arr.rend(); ++i)
{
    out.push_back(*i);
}

迭代器已經為您提供了一個值,而不是向量的索引。

下標運算符中的表達式

out.push_back(arr[*i]);
              ^^^^^^^   

沒有道理。

你的意思是

out.push_back( *i );

但是無論如何,函數可以這樣更好地編寫,以創建新的反向矢量

#include <iostream>
#include <vector>
#include <iterator>


std::vector<int> reverse( const std::vector<int> &v ) 
{
    std::vector<int> out;
    out.reserve( v.size() );

    for ( auto first = std::rbegin( v ), last = std::rend( v ); first != last; ++first )
    {
        out.push_back( *first );
    }

    return out;
}

int main() 
{
    std::vector<int> v = { 4, 3, 2, 1 };

    for ( const auto &item : v ) std::cout << item << ' ';
    std::cout << '\n';

    auto reversed_v = reverse( v );

    for ( const auto &item : reversed_v ) std::cout << item << ' ';
    std::cout << '\n';

    return 0;
}

程序輸出為

4 3 2 1 
1 2 3 4

或像這樣將向量反向

#include <iostream>
#include <vector>
#include <iterator>
#include <algorithm>


void reverse( std::vector<int> &v ) 
{
    if ( not v.empty() )
    {
        for ( auto first = std::rbegin( v ), last = std::rend( v ); first < --last; ++first )
        {
            std::iter_swap( first, last );
        }
    }       
}

int main() 
{
    std::vector<int> v = { 4, 3, 2, 1 };

    for ( const auto &item : v ) std::cout << item << ' ';
    std::cout << '\n';

    reverse( v );

    for ( const auto &item : v ) std::cout << item << ' ';
    std::cout << '\n';

    return 0;
}

程序輸出與上圖相同

4 3 2 1 
1 2 3 4

另外,也可以使用相應的標准算法std::reverse_copystd::reverse

盡可能在標准庫中優先使用算法,而不是手工制作的循環,因為:
1)它們更具表現力;
2)他們可能會更有效率。

std::reverse(std::begin(arr), std::end(arr));

只需包含“ algorithm”標頭即可使用std :: reverse。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM