为什么 std::search 需要前向迭代
我的问题与下面的线程相同,我正在努力理解给出的答案,或者更确切地说,我的代码不应该工作,因为它只使用输入迭代器..但我的 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 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
您误解了输入迭代器的功能。
您无法“保存”或复制输入迭代器。它允许您只遍历序列一次。换句话说,这一行以及其他行将中断:
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.