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

Как работает "полиморфизм"?

13.01.2020, 02:09. Показов 1880. Ответов 10
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Увидел код на лекции, в ютюбе, где объясняли, что текущий полиморфизм в С++ может быть еще быстрее:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
template<class _Ty>
class A {
public:
    int a;
    void Fun() {
        static_cast<_Ty*>(this)->Fun();
        std::cout << "A\n";
    }
};
 
class B : public A<B> {
public:
    int a;
    void Fun() {
        std::cout << "B\n";
    }
};
 
int main(){
    A<B> *t = new B;
    t->Fun();
}
По правде сказать, такого кол-ва непонятных моментов в одном месте, давно не видел. Как это вообще работает? Т.к. я вроде понимаю..но вроде и нет

static_cast<_Ty*>(this)->Fun(); - не до конца понимаю эту запись. Т.к. при приведении типов, апкаст, переменные себя ведут, наверное, схожим образом, то есть, данные класса выше(по иерархии) остаются, сохраняются. Но...это же переменные; у них, по факту, даже адреса всё также по порядку идут. А функции как? Т.к. я понимаю принцип работы, в данном случае, но не понимаю, как оно устроено "под капотом".

Буду благодарен за развернутый ответ
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
13.01.2020, 02:09
Ответы с готовыми решениями:

Как работает полиморфизм в C++ на уровне оперативной памяти
Здравствуйте! Возник вопрос чисто теоретического характера. Я знаю (или думаю, что знаю), по каким принципам работает апкаст и...

Объясните как работает полиморфизм на моем примере
Здравствуйте уважаемые. Пожалуйста объясните на моем примере, как это работает. Выдержки из моего кода. class Instrumenti { ...

Не работает полиморфизм
Почему объект использует метод базового класса? Базовый класс: #pragma once #include &quot;System.h&quot; #include...

10
Вездепух
Эксперт CЭксперт С++
 Аватар для TheCalligrapher
12925 / 6793 / 1819
Регистрация: 18.10.2014
Сообщений: 17,190
13.01.2020, 03:13
Лучший ответ Сообщение было отмечено MJ_PRUTYG как решение

Решение

Упростите пример - уберите шаблонность. Получим эквивалентный пример без шаблонов

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
class A {
public:
    int a;
    void Fun();
};
 
class B : public A {
public:
    int a;
    void Fun() {
        std::cout << "B\n";
    }
};
 
void A::Fun() {
    static_cast<B*>(this)->Fun();
    std::cout << "A\n";
}
 
int main(){
    A *t = new B;
    t->Fun();
}
Что именно вам здесь не понятно?

Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
Т.к. при приведении типов, апкаст,
О каком именно приведении типов вы ведете речь? static_cast здесь - это downcast, а не upcast.

Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
переменные себя ведут, наверное, схожим образом, то есть, данные класса выше(по иерархии) остаются, сохраняются.
Ни понял вопроса. При чем здесь данные класса и как они могут "не сохраняться"? Приведение типа в данном случае применяется к указателю. На сам объект и какие-либо "данные" это, разумеется, никак не влияет и влиять не может. Они тут вообще никак не участвуют.

Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
что текущий полиморфизм в С++ может быть еще быстрее
Никакого "полиморфизма" в этом коде нет, в классическом понимании термина. Полиморфизм в С++ требует наличия абстрактного общего предка для группы полиморфных классов. В этом коде нет ни общего предка, ни группы полиморфных классов.

Это то, что иногда называют "полиморфизмом времени компиляции". На классический полиморфизм это даже отдаленно не похоже и никак с ним не конкурирует. Поэтому сравнивать их в терминах "еще быстрее" - бессмысленно.
1
2784 / 1937 / 570
Регистрация: 05.06.2014
Сообщений: 5,602
13.01.2020, 07:52
Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
По правде сказать, такого кол-ва непонятных моментов в одном месте, давно не видел. Как это вообще работает?
Это попытка навелосипедить девиртуализацию. Неактуально ввиду того что компиляторы уже научились делать подобные оптимизации самостоятельно.
1
 Аватар для zayats80888
6352 / 3523 / 1428
Регистрация: 07.02.2019
Сообщений: 8,995
13.01.2020, 08:12
MJ_PRUTYG, CRTP
2
3 / 3 / 0
Регистрация: 28.11.2018
Сообщений: 242
14.01.2020, 08:14  [ТС]
Renji, почему не актуально? Т.к. уже несколько человек говорили что используют сей метод для оптимизации ""полиморфизма""
0
2784 / 1937 / 570
Регистрация: 05.06.2014
Сообщений: 5,602
14.01.2020, 08:32
Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
Renji, почему не актуально? Т.к. уже несколько человек говорили что используют сей метод для оптимизации ""полиморфизма""
Потому что этот метод уже использует встроенный оптимизатор кода.
У одной виртуальной функции Fun может быть множество различных реализаций. Ради этого ее собственно и делают виртуальной. Чтобы разобраться какая конкретно реализация вам нужна, программа должна лезть в таблицу виртуальных функций. А это дополнительные телодвижения. Если вы точно знаете какая из реализаций нужна, ее можно вызвать напрямую. Что собственно в вашем примере и делается.

Проблема в том, что компиляторы уже достаточно умные чтобы увидеть "Эй, да нет тут никакого множества реализаций! У Fun всего одна версия" и не забивать себе голову какими-то там таблицами. А так как все необходимые оптимизации и так уже делает компилятор, вы только попусту усложняете код.
0
Mental handicap
 Аватар для Azazel-San
1246 / 624 / 171
Регистрация: 24.11.2015
Сообщений: 2,429
14.01.2020, 11:44
Цитата Сообщение от Renji Посмотреть сообщение
А так как все необходимые оптимизации и так уже делает компилятор, вы только попусту усложняете код.
Ну, не все компиляторы это делают, а те, что делают не дают никаких гарантий, даже с максимальными оптимизациями.
0
2784 / 1937 / 570
Регистрация: 05.06.2014
Сообщений: 5,602
14.01.2020, 11:57
Цитата Сообщение от Azazel-San Посмотреть сообщение
Ну, не все компиляторы это делают, а те, что делают не дают никаких гарантий, даже с максимальными оптимизациями.
На Хабре эта оптимизация еще семь лет тому назад разбиралась, на примере gcc и clang. Думаю, уж за семь лет то оно точно расползлось по всем популярным компиляторам.
0
Mental handicap
 Аватар для Azazel-San
1246 / 624 / 171
Регистрация: 24.11.2015
Сообщений: 2,429
14.01.2020, 12:15
Цитата Сообщение от Renji Посмотреть сообщение
Думаю, уж за семь лет то оно точно расползлось по всем популярным компиляторам.
А, так это были всего лишь ваши догадки?
https://godbolt.org/z/yNeygW
0
Эксперт С++
 Аватар для hoggy
8973 / 4319 / 960
Регистрация: 15.11.2014
Сообщений: 9,760
14.01.2020, 12:31
Цитата Сообщение от Renji Посмотреть сообщение
Это попытка навелосипедить девиртуализацию. Неактуально ввиду того что
ввиду того, что бред.

бред потому что вместо девиртуализации получается отказ от виртуальности вообще.
причем завуалированным (через жопнутым) способом.

код, который написан в стартопике можно переписать гораздо проще:

C++
1
2
3
4
5
6
7
8
9
10
11
struct B
{
    void Fun() const noexcept {  std::cout << "B\n"; }
};
 
int main()
{
    B* obj = new B;
    obj->Fun();
    delete obj;
}
вот такой интерфейс:
Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
A<B>
- не нужен.
это бред.

с таким же успехом можно сразу использовать тип B,
и не морочить голову ни себе, ни людям.

Цитата Сообщение от MJ_PRUTYG Посмотреть сообщение
Увидел код на лекции, в ютюбе,
передай этому чуваку с ютюба: Шарик, ты - балбес.
и скинь ему эту ссылку
2
3 / 3 / 0
Регистрация: 28.11.2018
Сообщений: 242
14.01.2020, 17:09  [ТС]
Цитата Сообщение от hoggy Посмотреть сообщение
с таким же успехом можно сразу использовать тип B
Вот, да, и я об этом! Такие же мысли. Просто зачем так морочиться, если всё равно знаешь что будет вызываться и из-за этого сама суть виртуальности пропадает.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
14.01.2020, 17:09
Помогаю со студенческими работами здесь

Как реализован полиморфизм?
Если я не ошибаюсь, то, благодаря ему, если member-функция fun в базовом классе CBase объявлена как virtual, и перегружена в производном...

Как реализовать полиморфизм
У меня товарищ ходил на собеседовании по работе и там у него спросили как реализовать полиморфизм в си(именно си а не с++) он не знал...

Как правильно реализовать полиморфизм?
Имеется такая иерархия классов //classes.h class CL1 { private: int x; virtual char c;

Как реализовать полиморфизм в игре пятнашки?
Здравствуйте нужно реализовать полиморфизм в игре пятнашки на окнах windows forms. То есть создать abstract класс в котором должен быть...

Как понять данный код (Полиморфизм)?
Здравствуйте! Только начал учить java, до этого кодил на php. Есть код: Строка 24 public class Shape { public void draw() { ...


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

Или воспользуйтесь поиском по форуму:
11
Ответ Создать тему
Новые блоги и статьи
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка.
Programma_Boinc 23.12.2025
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка. Рецензия / Мнение Это мой обзор планшета X220 с точки зрения школьника. Недавно я решила попытаться уменьшить свой. . .
PhpStorm 2025.3: WSL Terminal всегда стартует в ~
and_y87 14.12.2025
PhpStorm 2025. 3: WSL Terminal всегда стартует в ~ (home), игнорируя директорию проекта Симптом: После обновления до PhpStorm 2025. 3 встроенный терминал WSL открывается в домашней директории. . .
Как объединить две одинаковые БД Access с разными данными
VikBal 11.12.2025
Помогите пожалуйста !! Как объединить 2 одинаковые БД Access с разными данными.
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru