Форум программистов, компьютерный форум CyberForum.ru

Использование пользовательского итератора для работы с STL алгоритмами: как определить typedef iterator_traits? - C++

Восстановить пароль Регистрация
Другие темы раздела
C++ переопределение защищенных методов http://www.cyberforum.ru/cpp-beginners/thread963485.html
При вызове метода basePubMethod() класса ChildClass возвращается 0. Как заставить его возвращать 1, не переопределяя basePubMethod() ? Аналогичный код на Java возвращает 1 class BaseClass { public: BaseClass() {} int basePubMethod() { return test(); }
C++ Ошибка с подключением русского языка А так же, почему то выделяет красным число "pi" #include <stdio.h> #include <math.h> #include <windows.h> char bufRus; char* Rus(const char*text) { CharToOem(text, bufRus); return bufRus; http://www.cyberforum.ru/cpp-beginners/thread963475.html
Posix C++
Подскажите,пожалуйста,как подключить posix к c++?или его нужно скачать и установить?
C++ Квадратичный массив, сумма элементов
Разработать программу, которая создаёт квадратную матрицу целых чисел размером N*N.Заполнить матрицу случайными числами. На главной диагонали разместить суммы элементов, которые лежат на той же строке и том же столбце. Массив ввел, уже готов и выводить, но не могу разобраться как посчитать сумму. #include "stdafx.h" #include <iostream> #include <iomanip> using namespace std;
C++ Структуры. Неправильно считывает строку http://www.cyberforum.ru/cpp-beginners/thread963394.html
Само задание: В текстовом файле хранится база отдела кадров предприятия. Каждая строка файла содержит запись об одном сотруднике. Формат записи: фамилия и инициалы (не более 30 поз., фамилия должна начинаться с первой позиции), год рождения (не более 5 поз.), оклад (не более 10 поз.). Написать программу, которая по заданной фамилии выводит на экран сведения о сотруднике, подсчитывая средний...
C++ Выход из программы Возможно, глупый вопрос, но как сделать выход из программы? Хочется сделать закрытие программы не из главной функции. К примеру: #include "stdafx.h" void func() { //выход из программы. Что-то вроде Application->exit(); } int _tmain(int argc, _TCHAR* argv) { подробнее

Показать сообщение отдельно
Cynacyn
 Аватар для Cynacyn
33 / 33 / 0
Регистрация: 02.05.2013
Сообщений: 109
27.09.2013, 11:57     Использование пользовательского итератора для работы с STL алгоритмами: как определить typedef iterator_traits?
Здравствуйте! Есть класс итератора:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
typedef vector<char> Line;
 
//-------------------------------------------------------
 
class Text_iterator {
    list<Line>::iterator ln;
    list<Line>::const_iterator line_end; // end list<Line> line.cend();
    Line::iterator pos;
public:
    typedef forward_iterator_tag iterator_category; // подсмотрено в std::vector
 
    Text_iterator(list<Line>::iterator ll, Line::iterator pp, list<Line>::const_iterator _end)
        :   ln(ll), pos(pp), line_end(_end) {}
    
    char& operator*() { 
        return *pos; 
    }
    
    Text_iterator& operator++() {
        ++pos;
        if(pos==ln->end()) {
            ++ln;
            if(ln!=line_end) pos=ln->begin();
        }
        return *this;
    }
 
    bool operator==(const Text_iterator& other) const {
        return (ln==other.ln && pos==other.pos);
    }
    bool operator!=(const Text_iterator& other) const {
        return !(*this==other);
    }
};
остальной контекст использования итератора (немного кода), под спойлером:
Кликните здесь для просмотра всего текста
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
#include <iostream>
using std::istream;
 
#include <vector>
using std::vector;
 
#include <list>
using std::list;
 
#include <algorithm>
using std::find;
 
#include <iterator>
using std::forward_iterator_tag;
 
//-------------------------------------------------------
// helper; my realisation of advance
template<class Iter>
Iter advance(Iter p, int n) 
{
    if(!n) return p;
    while(n>0) { p++; n--; }
    while(n<0) { p--; n++; }
    return p;
}
 
//-------------------------------------------------------
 
typedef vector<char> Line;
 
//-------------------------------------------------------
 
class Text_iterator {
    list<Line>::iterator ln;
    list<Line>::const_iterator line_end; // end list<Line> line.cend();
    Line::iterator pos;
public:
    typedef forward_iterator_tag iterator_category;
 
    Text_iterator(list<Line>::iterator ll, Line::iterator pp, list<Line>::const_iterator _end)
        :   ln(ll), pos(pp), line_end(_end) {}
    
    char& operator*() { 
        return *pos; 
    }
    
    Text_iterator& operator++() {
        ++pos;
        if(pos==ln->end()) {
            ++ln;
            if(ln!=line_end) pos=ln->begin();
        }
        return *this;
    }
 
    bool operator==(const Text_iterator& other) const {
        return (ln==other.ln && pos==other.pos);
    }
    bool operator!=(const Text_iterator& other) const {
        return !(*this==other);
    }
};
 
//-------------------------------------------------------
 
struct Document {
    list<Line> line;
    
    Document() { line.push_back(Line()); }
    
    Text_iterator begin() {
        return Text_iterator(line.begin(), line.begin()->begin(), line.cend()); 
    }
    Text_iterator end() {
        //return Text_iterator(line.end(), line.end()->end());  // Expression: list iterator not dereferencable
    
        list<Line>::iterator last_line=line.begin();
        list<Line>::iterator it=line.begin();
        
        it++;
        for(; it!=line.end(); it++, last_line++);
                    
        return Text_iterator(line.end(), 
            last_line->end(), 
            line.cend()); 
    }
    
    bool empty() const
    {
        if(line.size()==1 && !line.begin()->size()) return true;
        else return false;
    }
};
 
//-------------------------------------------------------
 
istream& operator>>(istream& is, Document& d) 
{
    char ch;
    while(is.get(ch)) {
        d.line.back().push_back(ch);
        if(ch=='\n')
            d.line.push_back(Line());
    }
    return is;
}
 
//-------------------------------------------------------
 
void print(Document& d) 
{
    if(d.empty()) return;
    for(Text_iterator it=d.begin(); it!=d.end();++it)
        std::cout <<*it;
}
 
//-------------------------------------------------------
 
void erase_line(Document& d, int n) 
{
    if(d.empty() || n<0 || d.line.size()<=n) return;
    d.line.erase(advance(d.line.begin(), n));
}
 
//-------------------------------------------------------
 
bool match(Text_iterator first, Text_iterator last, const string& s)
{
    int i=0;
    for(Text_iterator it=first; it!=last && i<s.size(); it++, i++) 
        if(*it!=s[i]) return false;
    
    return true;
}
 
//-------------------------------------------------------
 
Text_iterator find_txt(Text_iterator first, Text_iterator last, const string& s)
{
    if(!s.size()) return last;
    char first_char=s[0];
    while(true) {
        Text_iterator p = find(first,last,first_char);
        if(p==last || match(p,last,s)) return p;
    }
}
 
//-------------------------------------------------------


при попытке использовать итераторы с std::find, компилятор начинает ругаться:
Кликните здесь для просмотра всего текста
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
1>------ Построение начато: проект: EmptyConsole01, Конфигурация: Debug Win32 ------
1>  code.cpp
1>f:\projects\new\emptyconsole01\emptyconsole01\Document.h(121): warning C4018: <=: несоответствие типов со знаком и без знака
1>f:\projects\new\emptyconsole01\emptyconsole01\Document.h(130): warning C4018: <: несоответствие типов со знаком и без знака
1>f:\projects\new\emptyconsole01\emptyconsole01\Document.h(130): warning C4620: не найдена постфиксная форма "operator ++" для типа "Text_iterator"; используется префиксная форма
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(33): см. объявление "Text_iterator"
1>f:\VSE2010\VC\include\xutility(386): error C2039: value_type: не является членом "Text_iterator"
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(33): см. объявление "Text_iterator"
1>          f:\VSE2010\VC\include\xutility(740): см. ссылку на создание экземпляров класса шаблон при компиляции "std::iterator_traits<_Iter>"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>          f:\VSE2010\VC\include\algorithm(72): см. ссылку на создание экземпляров функции шаблон при компиляции "void std::_Debug_range<_InIt>(_InIt,_InIt,std::_Dbfile_t,std::_Dbline_t)"
1>          with
1>          [
1>              _InIt=Text_iterator
1>          ]
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(143): см. ссылку на создание экземпляров функции шаблон при компиляции "_InIt std::find<Text_iterator,char>(_InIt,_InIt,const _Ty &)"
1>          with
1>          [
1>              _InIt=Text_iterator,
1>              _Ty=char
1>          ]
1>f:\VSE2010\VC\include\xutility(386): error C2146: синтаксическая ошибка: отсутствие ";" перед идентификатором "value_type"
1>f:\VSE2010\VC\include\xutility(386): error C4430: отсутствует спецификатор типа - предполагается int. Примечание. C++ не поддерживает int по умолчанию
1>f:\VSE2010\VC\include\xutility(386): error C2602: std::iterator_traits<_Iter>::value_type не является членом базового класса "std::iterator_traits<_Iter>"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>          f:\VSE2010\VC\include\xutility(386): см. объявление "std::iterator_traits<_Iter>::value_type"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(386): error C2868: std::iterator_traits<_Iter>::value_type: недопустимый синтаксис для "using"-объявления; требуется полное имя
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(387): error C2039: difference_type: не является членом "Text_iterator"
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(33): см. объявление "Text_iterator"
1>f:\VSE2010\VC\include\xutility(387): error C2146: синтаксическая ошибка: отсутствие ";" перед идентификатором "difference_type"
1>f:\VSE2010\VC\include\xutility(387): error C4430: отсутствует спецификатор типа - предполагается int. Примечание. C++ не поддерживает int по умолчанию
1>f:\VSE2010\VC\include\xutility(387): error C2602: std::iterator_traits<_Iter>::difference_type не является членом базового класса "std::iterator_traits<_Iter>"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>          f:\VSE2010\VC\include\xutility(387): см. объявление "std::iterator_traits<_Iter>::difference_type"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(387): error C2868: std::iterator_traits<_Iter>::difference_type: недопустимый синтаксис для "using"-объявления; требуется полное имя
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(389): error C2039: pointer: не является членом "Text_iterator"
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(33): см. объявление "Text_iterator"
1>f:\VSE2010\VC\include\xutility(389): error C2146: синтаксическая ошибка: отсутствие ";" перед идентификатором "pointer"
1>f:\VSE2010\VC\include\xutility(389): error C4430: отсутствует спецификатор типа - предполагается int. Примечание. C++ не поддерживает int по умолчанию
1>f:\VSE2010\VC\include\xutility(389): error C2602: std::iterator_traits<_Iter>::pointer не является членом базового класса "std::iterator_traits<_Iter>"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>          f:\VSE2010\VC\include\xutility(389): см. объявление "std::iterator_traits<_Iter>::pointer"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(389): error C2868: std::iterator_traits<_Iter>::pointer: недопустимый синтаксис для "using"-объявления; требуется полное имя
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(390): error C2039: reference: не является членом "Text_iterator"
1>          f:\projects\new\emptyconsole01\emptyconsole01\Document.h(33): см. объявление "Text_iterator"
1>f:\VSE2010\VC\include\xutility(390): error C2146: синтаксическая ошибка: отсутствие ";" перед идентификатором "reference"
1>f:\VSE2010\VC\include\xutility(390): error C4430: отсутствует спецификатор типа - предполагается int. Примечание. C++ не поддерживает int по умолчанию
1>f:\VSE2010\VC\include\xutility(390): error C2602: std::iterator_traits<_Iter>::reference не является членом базового класса "std::iterator_traits<_Iter>"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>          f:\VSE2010\VC\include\xutility(390): см. объявление "std::iterator_traits<_Iter>::reference"
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
1>f:\VSE2010\VC\include\xutility(390): error C2868: std::iterator_traits<_Iter>::reference: недопустимый синтаксис для "using"-объявления; требуется полное имя
1>          with
1>          [
1>              _Iter=Text_iterator
1>          ]
========== Построение: успешно: 0, с ошибками: 1, без изменений: 0, пропущено: 0 ==========

Насколько я понял, нужно опеределить эти typedef'ы iterator_traits:
difference_type
value_type
pointer
reference
iterator_category
Но походу обучения я работал с ними очень поверхностно, по идее автор учебника подразумавает что код должен работать и так (или это такое датское коварство). Помогите пожалуйста.
Заранее спасибо.

Добавлено через 7 минут
Пока что определил так.
C++
1
2
3
4
5
    typedef forward_iterator_tag iterator_category;
    typedef ptrdiff_t difference_type;
    typedef char value_type;
    typedef char* pointer;
    typedef char& reference;
Компилируется работает.
Думаю тему можно закрывать.
Спасибо за внимание.
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
 
Текущее время: 10:33. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru