lightalex
@lightalex

Как правильно переопределить функции и типы при наследовании класса?

Доброго времени суток!
Пытаюсь переопределить функцию и тип переменной при наследовании класса.
Собственно код:
#include <stdio.h>
#include <iostream>
#include <typeinfo>

class A {
public:
    A(){};
    ~A(){};
    
    typedef int custom;
    
    custom num = 1;
    
    int get() {
        return 1;
    }
    void print() {
        std::cout << get() << " " << typeid(num).name() << "\n";
    }
};
class B : public A {
public:
    B() : A(){};
    ~B(){};
    
    typedef float custom;
    
    int get() {
        return 2;
    }
};

int main() {
    B b;
    b.print();

    return 0;
}

Мне нужно чтобы вывело 2 f, но сейчас выводит 1 i.
Я пытаюсь добиться этого без переопределения функции get
Возможно ли это сделать? Если да, то как?
  • Вопрос задан
  • 142 просмотра
Решения вопроса 2
vt4a2h
@vt4a2h Куратор тега C++
Senior software engineer (C++/Qt/boost)
Да, это можно сделать, но вам необходимо использовать шаблоны. Что-то вроде:
#include <stdio.h>
#include <iostream>
#include <typeinfo>

template <class T>
class A {
public:
    A(){};
    ~A(){};
    
    typedef T custom;
    
    custom num = 1;
    
    T get() {
        return num;
    }
    void print() {
        std::cout << get() << " " << typeid(num).name() << "\n";
    }
};

class B : public A<float> {
public:
    B() : A() { num = 2.f; };
    ~B(){};
};

int main() {
    B b;
    b.print();

    return 0;
}


PS
Я просто немного поправил код автора...
Ответ написан
Комментировать
reverse_kacejot
@reverse_kacejot
Junior C++ Developer, bachelor of Applied Math
Мне нужно знать, зачем Вы хотите такое сделать, иначе не понятно, почему пытаетесь использовать перегрузку типов (которой нет).

Если Вам нужно полиморфное поведение - воспользуйтесь виртуальными функциями.
Теперь разберем Ваш код в одном месте:
typedef float custom;
Здесь не происходит ничего иного, кроме как объявления имени в области видимости класса B. Как я говорил выше переопределять типы нельзя, и от написанного Вами кода, тип custom в А не поменяется. Иными словами у вас будет два типа:
A::custom = int
B::custom = float


Что Вам нужно сделать:
class I
{
public:
    virtual void print() = 0;
};

class A : public I
{
public:
    virtual void print() override 
    {
        std::cout << num;
    }

private:
    int num = 1;
};

class B : public I
{
public:
    virtual void print() override 
    {
        std::cout << num;
    }

private:
    float num = 2.f;
};


Иерархии из трех классов можно избежать, написав простой шаблон:

template <typename T>
class A
{
public:
    void print()
    {
        std::cout << val;
    }

private:
    T val;
};
Ответ написан
Комментировать
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы