Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.67/3: Рейтинг темы: голосов - 3, средняя оценка - 4.67
0 / 0 / 0
Регистрация: 15.04.2020
Сообщений: 22
1

Не получается использовать указатель на метод класса

26.04.2020, 22:16. Показов 561. Ответов 9
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Добрый вечер!
Пишу код по учебе, хотел использовать указатель на функцию, чтобы указывал на метод класса getArea и на подобные, которые планирую добавить в дальнейшем.
Наверняка простая ошибка по синтаксису, помогите, пожалуйста. Попытка создания указателя на функцию и его использования - в самом низу кода.



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
#include <iostream>
#include <cmath>
 
using namespace std;
 
class Shape
{
    public:
    virtual void showShape()=0;
    virtual double getArea()=0;
    friend std::ostream& operator <<(std::ostream &out, const Shape &p)
    {
        return p.print(out);
    }
    virtual std::ostream& print(std::ostream &out) const =0;
    ~ Shape()
    {
    }
 
};
 
class Point
{
public:
    int m_x = 0;
    int m_y = 0;
 
 
    Point(int x, int y)
        : m_x(x), m_y(y)
    {
 
    }
 
    friend std::ostream& operator<<(std::ostream &out, const Point &p)
    {
        out << "Point(" << p.m_x << ", " << p.m_y  << ")";
        return out;
    }
    virtual std::ostream& print(std::ostream &out) const //override
    {
        out<<m_x<<m_y;
        return out;
    }
    
};
 
class Triangle: public Shape
{
private:
    Point m_1, m_2, m_3;
    
public:
    Triangle(Point f, Point s, Point t): m_1(f), m_2(s), m_3(t)
    {
    }
    virtual void showShape()
    {
        cout<<"  ."<<'\n'<<
              " ..."<<'\n'<<
              "....."<<endl;
    }
    virtual double getArea()
    {
        double det=1*(m_1.m_x*m_2.m_y-m_1.m_y*m_2.m_x)-1*(m_1.m_x*m_3.m_y-m_3.m_x*m_1.m_y)+1*(m_2.m_x*m_3.m_y-m_3.m_x*m_2.m_y);
        double S=.5*fabs(det);
        return S;
    }
    virtual std::ostream& print(std::ostream &out) const// override
    {
        out<<"Triangle(" <<m_1<<", " <<m_2<<", " <<m_3<<")";
        return out;
    }
    
};
 
class Circle: public Shape
{
private:
    Point m_cntr;
    int m_radius;
public:
    Circle(Point cntr, int radius): m_cntr(cntr), m_radius(radius)
    {
    }
    virtual void showShape()
    {
        cout<<"    ."<<'\n'<<
              " .      ."<<'\n'<<
              ".        ."<<'\n'<<
              " .      ."<<'\n'<<
              "     ."<<endl;
    }
    virtual double getArea()
    {
        return(3.14*double(pow(m_radius,1)));
    }
    
    virtual std::ostream& print(std::ostream &out) const// override
    {
        out<<"Circle("<<m_cntr<<", radius "<<m_radius<<")";
        return out;
    }
};
 
int main()
{
    Circle c(Point(1, 2), 7);
    std::cout << c << '\n';
    cout<<c.getArea()<<endl;
    Triangle t(Point(1, 2), Point(4, 8), Point(7, 8));
    std::cout << t << '\n';
    cout<<t.getArea()<<endl;
    t.showShape();
    c.showShape();
 
 
    int op=1;
 
   
    double (*pFcn)()=nullptr; /// Здесь!
    switch(op) ///
    {
        case 1: pFcn=&Shape::getArea; break; ///
    }
    c.pFcn();
 
    return 0;
}
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
26.04.2020, 22:16
Ответы с готовыми решениями:

Как передать в метод класса Menu указатель на метод дочернего класса?
Как передать в метод базового класса указатель на метод дочернего: class Menu() { protected: ...

Функция, получающая указатель на обычную функцию, получает указатель на метод класса
Здравтсвуйте. Имеется вопрос по указателям на методы класса. Допустим, есть функция( f ), которая...

Указатель на метод класса в качестве аргумента метода класса
Функция _createFun вызывается для создания ХХХ в основном классе. Но вот потребовалось создать ХХХ...

При перегрузке оператора для класса не получается использовать имя переменной такое же, как в описании класса
Описал первый класс,затем - описал второй класс, используя первый,и когда начал перезагружать...

9
7787 / 6555 / 2983
Регистрация: 14.04.2014
Сообщений: 28,633
26.04.2020, 23:32 2
Зачем тебе это понадобилось? Усложняешь на ровном месте.
Указатель на функцию-член класса
0
Комп_Оратор)
Эксперт по математике/физике
8949 / 4703 / 629
Регистрация: 04.12.2011
Сообщений: 13,999
Записей в блоге: 16
26.04.2020, 23:43 3
kir0116, непонятно что вы хотите сделать. Виртуальный метод можно вызвать на указателе на объект базового класса Shape. Несмотря на то что не бывает таких объектов, бывают на них указатели. И ставить их можно на объекты наследников. То есть, логика ветвления тут реализуется иначе)
1
0 / 0 / 0
Регистрация: 15.04.2020
Сообщений: 22
27.04.2020, 00:07  [ТС] 4
Хотелось реализовать возможность в зависимости от введенного в input числа запускать определенный метод (например, 1- нахождение площади, 2 - какой-нибудь длины и т.д.). То есть смысл глобально никакой, хотелось в качестве упражнения просто отработать использование указателя на функцию.
И теперь интересно было бы понять, в чем тут ошибка, так как в случае с обычными функциями, вне каких-либо классов, это должно было бы сработать)
0
7787 / 6555 / 2983
Регистрация: 14.04.2014
Сообщений: 28,633
27.04.2020, 00:15 5
Я тебе дал ссылку. Там показано, как это записывается. Но польза в чём для твоей задачи?
0
0 / 0 / 0
Регистрация: 15.04.2020
Сообщений: 22
27.04.2020, 00:28  [ТС] 6
Польза - вот, как я выше написал. Глобально никакой пользы нет, вообще, хочется просто пощупать указатели на функции.
через typedef, как в той ветке по ссылке указано, я еще до этого пробовал
мне интересно, почему так, как в вышеприложенном варианте у меня, не прокатывает
0
7787 / 6555 / 2983
Регистрация: 14.04.2014
Сообщений: 28,633
27.04.2020, 00:40 7
Потому что для функции-члена особый способ записи, а ты берёшь как для простой.
1
Комп_Оратор)
Эксперт по математике/физике
8949 / 4703 / 629
Регистрация: 04.12.2011
Сообщений: 13,999
Записей в блоге: 16
27.04.2020, 00:56 8
kir0116, в случаях достаточно специфических, специфичность ситуации требует инструментария. Это значит, что взять уникльный иструмент и попытаться примитивными средствами сгенерировать ситуацию для применения, это похоже на попытку логарифмической линейкой проковырять дырку в промокашке.
Конкретно о указателях на функции лучше почитать. И обратите внимание на случаи, когда, это применяется. Если не поймёте, - ройте задачи.
0
Вездепух
Эксперт CЭксперт С++
11691 / 6370 / 1723
Регистрация: 18.10.2014
Сообщений: 16,053
27.04.2020, 01:11 9
Цитата Сообщение от kir0116 Посмотреть сообщение
C++
1
double (*pFcn)()=nullptr; /// Здесь!
Это не указатель на метод класса. Это указатель на обычную функцию. Указатель на обычную функцию не может указывать на [нестатический] метод класса.

Правильно:

C++
1
2
3
4
5
6
    double (Shape::*pFcn)()=nullptr;
    switch(op) ///
    {
        case 1: pFcn=&Shape::getArea; break;
    }
    (c.*pFcn)();
Добавлено через 5 минут
Цитата Сообщение от kir0116 Посмотреть сообщение
Хотелось реализовать возможность в зависимости от введенного в input числа запускать определенный метод (например, 1- нахождение площади, 2 - какой-нибудь длины и т.д.).
Это совершенно правильная логика. Именно и только для этого и предназначены указатели на члены классов. При желании, вы можете организовать такие указатели в массив, чтобы выполнять выбор метода не через switсh, а просто через индекс массива. Разумеется, такой указатель может указывать только на методы соответствующего типа.

И не обращайте внимание на попытки некоторых индивидуумов напускать дымовую завесу из потока малосвязанных друг с другом слов: вас (точнее - нас всех) просто пытаются троллить
1
Комп_Оратор)
Эксперт по математике/физике
8949 / 4703 / 629
Регистрация: 04.12.2011
Сообщений: 13,999
Записей в блоге: 16
27.04.2020, 09:50 10
kir0116, вызов метода класса, в общем случае, требует экземпляра класса. Та логика, о которой вы говорите - попытка сделать запуск независимым от встроенного инструментария.
Цитата Сообщение от kir0116 Посмотреть сообщение
Хотелось реализовать возможность в зависимости от введенного в input числа запускать определенный метод (например, 1- нахождение площади, 2 - какой-нибудь длины и т.д.).
То есть, язык предоставляет вам возможность выбора метода по имени. Для того, чтобы отказаться от этого нужно иметь вескую причину. Это может быть например запуск в виде обратного вызова. Допустим вы хотите создать механизм, который запускает разные методы, разных объектов в другом контексте, а логика выбора находится на вызывающей стороне. Тогда можно передать объект и указатель на метод класса, а запуск будет выполнен на той стороне. Привязка метода к объекту может быть выполнена по разному. Но важно то, что указатель на метод класса объявляется и используется иначе чем указатель на функцию. Это не просто разные синтаксисы. Указатель на метод - член, это другой тип, чем указатель на функцию. И это не самостоятельный тип.
Я повторю.
Цитата Сообщение от IGPIGP Посмотреть сообщение
Конкретно о указателях на функции лучше почитать.
Ваш код показывает существенно недостаточную подготовленность к вопросу. Тут нет ни какого троллинга. Написать вам пример как по свичу выдернуть метод схожий по сигнатуре? В сетке этого полно. Синтаксис ужасен (мнение не только моё). Почитайте и попробуйте запустить. Может и вопрос отпадёт. А может появятся новые. Нюансов там достаточно.

Добавлено через 11 минут
Еще непонятно, почему знакомясь с новой концепцией (непростой) вы сразу выбирает сложный контекст тестирования в виде виртуальных методов. Не лучше ли с самого простого начать? Это тоже не троллинг.
Вот я нашёл в старых примерах случай и с виртуальными методами. О чём говорилось не помню, но можете взглянуть:
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
#include <iostream>
 
using namespace std;
 
struct Base
{
    virtual ~Base(){};
    bool is_virtualCall;
    Base(bool b=true):is_virtualCall(b){}
    virtual void foo(){cout<<"\nfoo from base";}
};
 
struct Child :public Base
{
     ~Child(){};;
   Child(bool b=true):Base(b){}
   void foo()
   {
       if(is_virtualCall){
       cout<<"\nfoo from child";
       }
       else
            {
        Base::foo();
        }
       }
};
 
void cb_caller(Base &b, void(Base::*fun)(void))
{
    (b.*fun)();
}
 
int main()
{
Base base;
Child child_virt, child_novirt(false);
cb_caller(base, &Base::foo);
cb_caller(child_virt, &Base::foo);
cb_caller(child_novirt, &Base::foo);
 
    return 0;
}
1
27.04.2020, 09:50
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
27.04.2020, 09:50
Помогаю со студенческими работами здесь

Указатель на метод класса!
Ответьте пожалуйста на такой вопрос:Возможна ли такая ситуация и как ее реализовать правильно? Мне...

Указатель на метод класса
Собственно, проблема вот в чем. Есть класс и для него определен метод class ABC ....... public:...

Указатель на метод класса
Приветствую. Нужна помощь. Не работает указатель в данной программе: #include &lt;iostream&gt; #include...

Указатель на метод класса
Есть для этого какой-нибудь инструмент? Интересует именно не ссылка, а указатель. Хочется примерно...

Указатель на метод класса
Всем доброе утро! В объявлении класса SignalMathHandler объявляю указатель на метод этого же...

Указатель на метод класса
Доброго времени суток, форумчане. Необходимо получить указатель на размер вектора. Делаю из...


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

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