Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.89/19: Рейтинг темы: голосов - 19, средняя оценка - 4.89
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
1

Перегрузка операций '<<' и '>>'

17.10.2010, 16:52. Показов 3489. Ответов 32
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Добрый вечер всем
У меня вот такое задание:
Создайте класс, реализующий однонаправленную очередь. В интерфейс класса должны входить перегруженные операции:
1) добавить элемент в конец очереди (<<);
2) извлечь элемент из начала очереди (>>).

Вот что смог написать (что не мог я закоментил):
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
#include <string.h>
#include <iostream>
using namespace std;
class Ocher{
private:
    struct Element{     // структура, задающая элемент списка
        int key;        // поле для хранения данных
        Element *next;  // указатель на следующий элемент
    };
    Element* pbeg;//начало очереди
    Element* pend;//конец очереди
public:
    Ocher(){
        Element* pbeg = 0;
        Element* pend = 0;
    }
    int operator <<(int a);
    int operator >>(Element** pbeg);
    void print(){
        while (pbeg != 0){
            Element *ph = pbeg;
            pbeg=pbeg->next;
            cout<<" "<<ph->key;
        }
    }
}
int Ocher::operator << (int a){
    Element* ph = new Element;
    ph->key = a;
    ph->next = 0;
    if (*pend!=0){   //здесь везде подчеркивает знак '=', почему незнаю
        (*pend)->next = ph;
        *pend = ph;
    }
    else{
        *pbeg = ph;
        *pend = ph;
    }
    return 0;
}
 
int Ocher::operator>>(Element** pbeg){
    int d = (*pbeg)->key;
    Element* ph = *pbeg;
    *pbeg = (*pbeg)->next;
    delete ph;
    return d;
}
 
int main(){
    setlocale(LC_ALL,"Russian");
    Ocher w;
    int b,a;
    while(true){
        system("cls");
        cout<<"1) Заполнить очередь"<<endl;
        cout<<"2) Вывести на экран"<<endl;
        cout<<"3) Удалить элемент"<<endl;
        cout<<"0) Выход"<<endl;
        cout<<"Ввод: "; cin>>b;
        if (b == 1){
            system("cls");
            cout<<"Введите значение: ";
            cin>>a;
            w<<a;
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 2){
            system("cls");
            cout<<"Список: ";
            w.print;//здесь ошибка (из за точки), хочу что бы распечаталсся список
            while (true){
                cout<<"\n0) Выход: ";
                int z; cin>>z;
                if (z == 0) break;
                cin.clear();
                fflush(stdin);
                continue;
            }
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 3){
            //Здесь не знаю как сделать что бы из очереди удалился первый элемент
        }
        system("cls");
        if (b == 0) break;
 
    }
 
    return 0;
}
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
17.10.2010, 16:52
Ответы с готовыми решениями:

Перегрузка операций
Данная программа выполянет операции с дробями. Но у меня возникла проблема. Я создал сервисную...

Перегрузка операций
Начал изучать перегрузку операций, и чего-то вроде не понял или что... Вообщем не могу понять чего...

Перегрузка операций
Добрый день! Задание простенькое но не могу решить так как не получается перегрузка операций....

Перегрузка операций
Уважаемые программисты! Помогите новичку! Мне нужно написать программу, в которой реализуется...

32
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 17:20 2
Я думаю, смысл создавать подобный интерфейс для работы с очередью в том, чтобы можно было "сцеплять" операторы постановки и изъятия из очереди (навроде работы с потоками ввода-вывода С++). А для этого необходимо, чтобы операторы возвращали ссылку на объект-очередь, а в параметрах принимали ссылку на элемент. Вроде бы в библиотеке контейнеров Qt я уже видел что-то подобное.
Сделал так:
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
#include <iostream>
#include <stdexcept>
#include <cstdlib>
 
namespace my
{
    template<class T>
    class queue
    {
    
    public:
        
        queue();
        ~queue();
        
        queue<T>& operator << (const T& elem);
        queue<T>& operator >> (T& elem);
        
        bool empty() const;
        
    private:
    
        struct node
        {
            T       data;
            node*   next;
            
            node(const T& elem)
                : data(elem), next(NULL) {}
        };
        
        node*   m_pnHead;
        node*   m_pnTail;
    };
    
    template<class T>
    queue<T>::queue()
        : m_pnHead(NULL), m_pnTail(NULL) {}
        
    template<class T>
    queue<T>::~queue()
    {
        while(m_pnHead)
        {
            node* delnode = m_pnHead;
            m_pnHead = m_pnHead->next;
            delete delnode;
            delnode = NULL;
        }
    }
    
    template<class T>
    queue<T>& queue<T>::operator << (const T& elem)
    {
        node* newnode = new node(elem);
        if(!m_pnTail)
            m_pnHead = newnode;
        else
            m_pnTail->next = newnode;
        m_pnTail = newnode;
        return *this;
    }
    
    template<class T>
    queue<T>& queue<T>::operator >> (T& elem)
    {
        if(!m_pnHead)
            throw std::runtime_error("queue is already empty!");
        node* delnode = m_pnHead;
        m_pnHead = m_pnHead->next;
        
        elem = delnode->data;
        delete delnode;
        delnode = NULL;
        return *this;
    }
    
    template<class T>
    bool queue<T>::empty() const
    {
        return m_pnHead == NULL;
    }
}
 
int main()
{
    my::queue<int> iqueue;
    iqueue << 4 << 6 << 8; // Ставим элементы в очередь
    int a, b, c;
    iqueue >> a >> b >> c; // Вынимаем элементы из очереди
    std::cout << "a = " << a << ", b = " << b << ", c = " << c << std::endl;
    return EXIT_SUCCESS;
}
PS. А вот то, что ты не определил деcтруктор - плохо!
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 17:28  [ТС] 3
Цитата Сообщение от Nameless One Посмотреть сообщение
PS. А вот то, что ты не определил деcтруктор - плохо!
На счет диструктора, да. Я просто пока тестировал. Мне как то не оч понятен ваш код. Можете как то помочь мой просто исправить)))
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 17:34 4
Цитата Сообщение от robert19 Посмотреть сообщение
Можете как то помочь мой просто исправить)))
Зачем ты оператору >> передаешь адрес первого узла очереди? Он у тебя и так уже известен, хранится в переменной-члене pbeg (или this->pbeg, если указывать явно)
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 17:44  [ТС] 5
Цитата Сообщение от Nameless One Посмотреть сообщение
Зачем ты оператору >> передаешь адрес первого узла очереди? Он у тебя и так уже известен, хранится в переменной-члене pbeg (или this->pbeg, если указывать явно)
а что туда передавать нужно?
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 17:49 6
Смотря какого поведения ты ожидаешь от оператора.
Если такого (overed - это заранее объявленный объект твоего класса):
C++
1
int i = overed >>;
(вот только, если я не ошибаюсь, нельзя переопределять арность оператора) то прототип оператора должен быть таким:
C++
1
int operator >>(); // вроде бы неправильно
А если такого:
C++
1
2
int i, j, k;
overed >> i >> j >> k;
то таким:
C++
1
Ocher& operator >>(int& val);
1
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 17:55  [ТС] 7
Что то вообще не понимаю(((
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:00 8
Цитата Сообщение от robert19 Посмотреть сообщение
Что то вообще не понимаю(((
А ты постарайся. Ты вообще пробовал запускать мой пример?
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:05  [ТС] 9
Цитата Сообщение от Nameless One Посмотреть сообщение
А ты постарайся. Ты вообще пробовал запускать мой пример?
Нет. потому что мы так не учили как ты написал. И мне не понятно
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:07 10
Цитата Сообщение от robert19 Посмотреть сообщение
Нет. потому что мы так не учили как ты написал. И мне не понятно
используй гугл, Люк, и смотри в сторону шаблонов
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:14  [ТС] 11
Разве нельзя мой подредактировать. Я просто не могу понять что там изменить нужно
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:18 12
Цитата Сообщение от robert19 Посмотреть сообщение
Я просто не могу понять что там изменить нужно
А я уже написал, что нужно. И только не надо говорить, что
мы так не учили как ты написал. И мне не понятно
поскольку этот мой пост я писал, ориентируесь уже на твою версию программы.
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:22  [ТС] 13
да не я пытался так написать но выдает ошибки((
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:27 14
Цитата Сообщение от robert19 Посмотреть сообщение
да не я пытался так написать но выдает ошибки((
Покажи, что написал, и какие ошибки выдает
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:35  [ТС] 15
Да все практически осталось то же самое. Только дописал диструктор
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
#include <string.h>
#include <iostream>
using namespace std;
class List{
private:
    struct Element{     // структура, задающая элемент списка
        int key;        // поле для хранения данных
        Element *next;  // указатель на следующий элемент
    };
    Element* pbeg;//начало очереди
    Element* pend;//конец очереди
public:
    List(){
        Element* pbeg = 0;
        Element* pend = 0;
    }
    int operator <<(int a);
    int operator >>(int &a);
    void print();
    ~List(){
        if(pbeg){
            pend=pbeg;
            while (pbeg)
                pbeg=pbeg->next;
            delete pend;
            pend=pbeg;
        }
    }
}
int List::operator << (int a){
    Element* ph = new Element;
    ph->key = a;
    ph->next = 0;
    if (*pend!=0){
        (*pend)->next = ph;
        *pend = ph;
    }
    else{
        *pbeg = ph;
        *pend = ph;
    }
    return 0;
}
 
int List::operator>>(int &a){//сюда ты предлагал вставить вот это List& operator >>(int& val);
    int d = pbeg->key;
    Element* ph = pbeg;
    pbeg = pbeg->next;
    delete ph;
    return d;
}
 
void List::print(){
    while (pbeg != 0){
        Element *ph = pbeg;
        pbeg = pbeg->next;
        cout<<" "<<ph->key;
    }
}
 
int main(){
    setlocale(LC_ALL,"Russian");
    List w;
    int b,a;
    while(true){
        system("cls");
        cout<<"1) Заполнить очередь"<<endl;
        cout<<"2) Вывести на экран"<<endl;
        cout<<"3) Удалить элемент"<<endl;
        cout<<"0) Выход"<<endl;
        cout<<"Ввод: "; cin>>b;
        if (b == 1){
            system("cls");
            cout<<"Введите значение: ";
            cin>>a;
            w<<a;
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 2){
            system("cls");
            cout<<"Список: ";
            w.print;//здесь ошибка (из за точки), хочу что бы распечаталсся список
            while (true){
                cout<<"\n0) Выход: ";
                int z; cin>>z;
                if (z == 0) break;
                cin.clear();
                fflush(stdin);
                continue;
            }
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 3){
            //Здесь не знаю как сделать что бы из очереди удалился первый элемент
        }
        system("cls");
        if (b == 0) break;
 
    }
 
    return 0;
}
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:44 16
Замени в возвращаемом значении операторов int на List&, и в конце каждого из них пропиши
C++
1
return *this;
Замени 46 строку на
C++
1
a = pbeg->key;
Удаление первого элемента из очереди делай так:
C++
1
2
int b;
w >> b; // в b теперь хранится значение удаленного первого элемента очереди
Добавлено через 1 минуту
Цитата Сообщение от robert19 Посмотреть сообщение
C++
1
w.print;//здесь ошибка (из за точки), хочу что бы распечаталсся список
Забыл скобки:
C++
1
w.print();
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:44  [ТС] 17
error C2628: недопустимый "List" с последующим "int" (возможно, отсутствует ";")
error C2556: List List::operator <<(int): перегруженная функция отличается от "int List::operator <<(int)" только возвращаемым типом
error C2371: List::operator <<: переопределение; различные базовые типы
error C2678: бинарный "!=": не найден оператор, принимающий левый операнд типа "List::Element" (или приемлемое преобразование отсутствует)
1> c:\program files (x86)\microsoft visual studio 10.0\vc\include\system_error(432): или "bool std::operator !=(const std::error_condition &,const std::error_code &)"
1> при попытке сопоставить список аргументов "(List::Element, int)"
error C2819: тип "List::Element" не имеет перегруженный "operator ->"
error C2232: ->List::Element::next: левый операнд имеет тип "struct", используйте "."
error C2679: бинарный "=": не найден оператор, принимающий правый операнд типа "List::Element *" (или приемлемое преобразование отсутствует)
error C2679: бинарный "=": не найден оператор, принимающий правый операнд типа "List::Element *" (или приемлемое преобразование отсутствует)
error C2679: бинарный "=": не найден оператор, принимающий правый операнд типа "List::Element *" (или приемлемое преобразование отсутствует)
error C2440: return: невозможно преобразовать "int" в "List &"
error C2264: List::operator <<: ошибка в определении или объявлении функции; функция не вызвана
error C2088: <<: недопустимо для class
error C3867: List:rint: в вызове функции отсутствует список аргументов; используйте "&List:rint" для создания указателя на член
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 18:50 18
robert19, а теперь покажи, как ты объявил и описал операторы
0
29 / 29 / 7
Регистрация: 26.03.2010
Сообщений: 305
17.10.2010, 18:57  [ТС] 19
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
#include <string.h>
#include <iostream>
using namespace std;
class List{
private:
    struct Element{     // структура, задающая элемент списка
        int key;        // поле для хранения данных
        Element *next;  // указатель на следующий элемент
    };
    Element* pbeg;//начало очереди
    Element* pend;//конец очереди
public:
    List(){
        Element* pbeg = 0;
        Element* pend = 0;
    }
    int operator <<(int a);
    List& operator >>(List&);
    void print();
    ~List(){
        if(pbeg){
            pend=pbeg;
            while (pbeg)
                pbeg=pbeg->next;
            delete pend;
            pend=pbeg;
        }
    }
}
int List::operator << (int a){// если поменять на List&  List::operator <<  (int a)... Выдает ошибку
    Element* ph = new Element;
    ph->key = a;
    ph->next = 0;
    if (pend!=0){
        pend->next = ph;
        pend = ph;
    }
    else{
        pbeg = ph;
        pend = ph;
    }
    return *this;//тут ругается
}
 
List& List::operator>>(List&){
    int a = pbeg->key;
    Element* ph = pbeg;
    pbeg = pbeg->next;
    delete ph;
    return *this;
}
 
void List::print(){
    while (pbeg != 0){
        Element *ph = pbeg;
        pbeg = pbeg->next;
        cout<<" "<<ph->key;
    }
}
 
int main(){
    setlocale(LC_ALL,"Russian");
    List w;
    int b,a;
    while(true){
        system("cls");
        cout<<"1) Заполнить очередь"<<endl;
        cout<<"2) Вывести на экран"<<endl;
        cout<<"3) Удалить элемент"<<endl;
        cout<<"0) Выход"<<endl;
        cout<<"Ввод: "; cin>>b;
        if (b == 1){
            system("cls");
            cout<<"Введите значение: ";
            cin>>a;
            w<<a;
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 2){
            system("cls");
            cout<<"Список: ";
            w.print();//здесь ошибка (из за точки), хочу что бы распечаталсся список
            while (true){
                cout<<"\n0) Выход: ";
                int z; cin>>z;
                if (z == 0) break;
                cin.clear();
                fflush(stdin);
                continue;
            }
            cin.clear();
            fflush(stdin);
            continue;
        }
        if (b == 3){
            //Здесь не знаю как сделать что бы из очереди удалился первый элемент
        }
        system("cls");
        if (b == 0) break;
 
    }
 
    return 0;
}
error C2628: недопустимый "List" с последующим "int" (возможно, отсутствует ";")
error C2556: List List::operator <<(int): перегруженная функция отличается от "int List::operator <<(int)" только возвращаемым типом
error C2371: List::operator <<: переопределение; различные базовые типы
error C2264: List::operator <<: ошибка в определении или объявлении функции; функция не вызвана
error C2088: <<: недопустимо для class
0
Эксперт С++
5828 / 3479 / 358
Регистрация: 08.02.2010
Сообщений: 7,448
17.10.2010, 19:23 20
Разберем ошибки:
Цитата Сообщение от robert19 Посмотреть сообщение
если поменять на List& List::operator << (int a)... Выдает ошибку
Нужно читать внимательней:
Цитата Сообщение от Nameless One Посмотреть сообщение
Замени в возвращаемом значении операторов int на List&, и в конце каждого из них пропиши
C++
1
return *this;
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// если поменять на List&  List::operator <<  (int a)... Выдает ошибку
// и где же здесь ты поменял int на List& ?
int List::operator << (int a){
        Element* ph = new Element;
        ph->key = a;
        ph->next = 0;
        if (pend!=0){
                pend->next = ph;
                pend = ph;
        }
        else{
                pbeg = ph;
                pend = ph;
        }
        return *this;//тут ругается - ну ясен пень, *this - это ссылка на List, а в возвращаемом значении прописано int
}
Надо так:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
List& List::operator << (int a){// если поменять на List&  List::operator <<  (int a)... Выдает ошибку
        Element* ph = new Element;
        ph->key = a;
        ph->next = 0;
        if (pend!=0){
                pend->next = ph;
                pend = ph;
        }
        else{
                pbeg = ph;
                pend = ph;
        }
        return *this;
}
Пошли дальше...
C++
1
2
3
4
5
6
7
List& List::operator>>(List&){
 int a = pbeg->key; 
 Element* ph = pbeg;
 pbeg = pbeg->next;
 delete ph;
 return *this;
}
Было написано:
Цитата Сообщение от Nameless One Посмотреть сообщение
Замени 46 строку на
C++
1
a = pbeg->key;
А ты что сделал? Ты заменил тип аргумента оператора, и сделал a локальной. Зачем? Надо так:
C++
1
2
3
4
5
6
7
List& List::operator>>(int& a){
 a = pbeg->key; 
 Element* ph = pbeg;
 pbeg = pbeg->next;
 delete ph;
 return *this;
}
И не забудь соответственно изменить объявления операторов внутри класса
0
17.10.2010, 19:23
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
17.10.2010, 19:23
Помогаю со студенческими работами здесь

Перегрузка операций
Здравствуйте. Не могли бы вы мне помочь изменить программу? Мне нужно из обычной программы сделать...

Перегрузка операций
Требуется перегрузить операции сложения + и присваивания = Вопрос: почему при завершении метода,...

Перегрузка операций
C++ Перегрузка операций.. Помоги написать прогу Определить класс для работы с квадратной...

Перегрузка операций << и >>
Всем добрый день.. У меня такая проблема, не получается перегрузить операторы &lt;&lt; и &gt;&gt; для своего...

Перегрузка операций С++
Подскажете пожалуйста, как буквам &quot;А&quot; и &quot;В&quot; присвоить номера 10 и 11 вместо 17 и 18. // пр4.cpp:...

Перегрузка Операций C++
Прошу помочь с кодом(а именно задание &quot;е&quot;). Буду очень благодарен! Создать базовый класс...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru