为什么 std::search 需要前向迭代

发布于 2024-10-24 15:35:59 字数 4199 浏览 7 评论 0原文

我的问题与下面的线程相同,我正在努力理解给出的答案,或者更确切地说,我的代码不应该工作,因为它只使用输入迭代器..但我的 func 似乎工作并且行为与 std::search 相同。 .所以我不知所措,不愿意在没有正确理解的情况下继续前进...也许如果有人可以建议一个会破坏我的功能但不会破坏std::的输入

为什么我需要一个正向迭代器来实现我的自定义 std::search

我正在学习《加速》这本书 C++”,来自 Koenig & Moo。

练习 8-2 要求我在我的 拥有一些模板化函数 <算法>和<数字>,以及 指定我的迭代器类型 实施要求。

当尝试实现 std::search 时, 我确定我只需要“输入” 迭代器。

但是,看看实施情况 与我一起安装的 std::search 编译器,我可以看到他们使用 “向前”迭代器,但我不能 明白为什么,因为没有 需要写,只能读,输入 迭代器满足要求。

这里有人可以帮助我理解吗 请问这个?为什么我需要使用 要实现的“前向”迭代器 std::搜索?

提前致谢。

我的功能:

template <class In> 
In search(  In begin, In end, In begin2, In end2 )
{
    In found ;                      // iter: 1st element in pattern match(in content)
    In pattern_begin = begin2 ;     // iter: 1st element in search pattern.
    int flag = 0 ;                  // flag: partial match found?

    // search content for pattern 
    while (  begin < end  ) {

        // if pattern-match fails ..reset vars
        // & continue searching remaining content/elements
        if ( *begin != *begin2 ) {

            In ret ;                     
            begin2 = pattern_begin ;
            flag = 0 ;
            begin++ ;


        } else {
            // compare next element in pattern with next element in content.
            // if: 1st element of 'pattern' is found, store iter to it's pos
            // ..then if entire pattern is found, we can ret an iter to where it starts
            if ( flag == 0 ) { 
                found = begin ;
                flag = 1 ;
            }
            // inc iters to compare next elements in partial match
            begin++ ;
            begin2++ ;
        }

        // if: iter is 1-past end of search pattern
        // then entire pattern has been found 
        // return the iter to where it starts
        if( begin2 == end2 ) {  return found ;  }

    }

    // end of content reached, no complete pattern found
    // begin should? equal an iter 1-past the end of content
    return begin ;
}

驱动程序:

///* // Driver: custom::search(  b, e, b2, e2  ) 
#include <string>
#include <vector>
#include <iostream>
//#include <algorithm>
#include "library_algorithms.h"

int main() {

    // init string test
    std::string content = "fo The fox  foxu jumped  foxe foxy " ;
    std::string search_pattern = "foxy" ;

    // func test on string
    std::string::iterator ret_iter = 
    custom::search(  content.begin(), content.end(), search_pattern.begin(), search_pattern.end()  ) ;
    //std::search(  content.begin(), content.end(), search_pattern.begin(), search_pattern.end()  ) ;

    // output
    if (  ret_iter != content.end()  ) {

        std::cout << std::endl << std::endl << search_pattern << ": found at position: " << int(  ret_iter - content.begin()  ) << std::endl;

    } else { 

        std::cout << std::endl << std::endl << search_pattern << ": ...not found" << std::endl;
    }




    // Init vec test:
    // create content values in range:  10 20 30 <......> 9970 9980 9990
    std::vector<int> myvector;
    for (int i=1; i<1000; i++) myvector.push_back(i*10);

    // create pattern values to search for
    std::vector<int> pattern ;
    pattern.push_back( 3730 ) ;
    pattern.push_back( 3740 ) ;
    pattern.push_back( 3750 ) ;
    pattern.push_back( 3760 ) ;

    // test: func on vector<int>
    std::vector<int>::iterator it;
    it = custom::search (  myvector.begin(), myvector.end(), pattern.begin(), pattern.end() );

    // output
    if (it!=myvector.end())
    std::cout << std::endl << std::endl << "pattern found at position " << int(it-myvector.begin()) << std::endl;
    else
    std::cout << std::endl << std::endl << "pattern not found" << std::endl;





    return 0 ;

}

my issue is identical to the thread below, I'm struggling to understand the answers given, or rather my code shouldn't work as it only uses input iterators ..but my func appears to work and behave identically to std::search ..so I'm at a loss and loathe to move on without understanding properly ...maybe if someone can suggest an input that will break my function but not the std::

From Why do I need a Forward Iterator to implement my customized std::search :

I am studying the book "Accelerated
C++" from Koenig & Moo.

Exercise 8-2 ask me to implement on my
own some templatized functions from
<algorithm> and <numeric>, and to
specify what kind of iterator does my
implementation require.

When trying to implement std::search,
I determined that I need only "input"
iterators.

However, looking at the implementation
of std::search installed with my
compiler, I can see that they use
"forward" iterators, but I cannot
understand why, because there is no
need to write, only to read, and input
iterators meet the requirement.

Can anybody here help me to understand
this, please? Why would I need to use
"forward" iterators to implement
std::search?

Thanks in advance.

myfunction:

template <class In> 
In search(  In begin, In end, In begin2, In end2 )
{
    In found ;                      // iter: 1st element in pattern match(in content)
    In pattern_begin = begin2 ;     // iter: 1st element in search pattern.
    int flag = 0 ;                  // flag: partial match found?

    // search content for pattern 
    while (  begin < end  ) {

        // if pattern-match fails ..reset vars
        // & continue searching remaining content/elements
        if ( *begin != *begin2 ) {

            In ret ;                     
            begin2 = pattern_begin ;
            flag = 0 ;
            begin++ ;


        } else {
            // compare next element in pattern with next element in content.
            // if: 1st element of 'pattern' is found, store iter to it's pos
            // ..then if entire pattern is found, we can ret an iter to where it starts
            if ( flag == 0 ) { 
                found = begin ;
                flag = 1 ;
            }
            // inc iters to compare next elements in partial match
            begin++ ;
            begin2++ ;
        }

        // if: iter is 1-past end of search pattern
        // then entire pattern has been found 
        // return the iter to where it starts
        if( begin2 == end2 ) {  return found ;  }

    }

    // end of content reached, no complete pattern found
    // begin should? equal an iter 1-past the end of content
    return begin ;
}

driver:

///* // Driver: custom::search(  b, e, b2, e2  ) 
#include <string>
#include <vector>
#include <iostream>
//#include <algorithm>
#include "library_algorithms.h"

int main() {

    // init string test
    std::string content = "fo The fox  foxu jumped  foxe foxy " ;
    std::string search_pattern = "foxy" ;

    // func test on string
    std::string::iterator ret_iter = 
    custom::search(  content.begin(), content.end(), search_pattern.begin(), search_pattern.end()  ) ;
    //std::search(  content.begin(), content.end(), search_pattern.begin(), search_pattern.end()  ) ;

    // output
    if (  ret_iter != content.end()  ) {

        std::cout << std::endl << std::endl << search_pattern << ": found at position: " << int(  ret_iter - content.begin()  ) << std::endl;

    } else { 

        std::cout << std::endl << std::endl << search_pattern << ": ...not found" << std::endl;
    }




    // Init vec test:
    // create content values in range:  10 20 30 <......> 9970 9980 9990
    std::vector<int> myvector;
    for (int i=1; i<1000; i++) myvector.push_back(i*10);

    // create pattern values to search for
    std::vector<int> pattern ;
    pattern.push_back( 3730 ) ;
    pattern.push_back( 3740 ) ;
    pattern.push_back( 3750 ) ;
    pattern.push_back( 3760 ) ;

    // test: func on vector<int>
    std::vector<int>::iterator it;
    it = custom::search (  myvector.begin(), myvector.end(), pattern.begin(), pattern.end() );

    // output
    if (it!=myvector.end())
    std::cout << std::endl << std::endl << "pattern found at position " << int(it-myvector.begin()) << std::endl;
    else
    std::cout << std::endl << std::endl << "pattern not found" << std::endl;





    return 0 ;

}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

韶华倾负 2024-10-31 15:35:59

您误解了输入迭代器的功能。

您无法“保存”或复制输入迭代器。它允许您只遍历序列一次。换句话说,这一行以及其他行将中断:begin2 =pattern_begin

输入迭代器可能代表您无法轻松“倒回”的内容,例如从网络适配器接收的数据流。指向“6 个元素之前”的迭代器不再有意义,因为该数据可能不再在内存中可用。您只有流中的当前位置。

显然,为了正确实现搜索,您需要能够多次遍历序列的各个部分。

You've misunderstood what an input iterator can do.

You can't "save" or copy an input iterator. It allows you to traverse the sequence exactly once. In other words, this line, among others, will break: begin2 = pattern_begin.

An input iterator may represents something that you can't readily "rewind", like, say, the stream of data received from a network adapter. An iterator pointing to "6 elements ago" is no longer meaningful, because that data may no longer be available in memory. You only have the current position in the stream.

It should be obvious that in order to implement search correctly, you need to be able to traverse parts of the sequence more than once.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文