Форум программистов, компьютерный форум, киберфорум
C++
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.75/8: Рейтинг темы: голосов - 8, средняя оценка - 4.75
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255

Специализации шаблона функции или перезагрузка

04.09.2016, 16:46. Показов 1796. Ответов 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
#include <iostream>
#include <vector>
using namespace std;
 
class A {};
vector<A*> List;
 
class B : public A
{
public:
    virtual void printB()
    {
        cout << "B" << endl;
    }
};
 
class B2 : public B
{
    void printB()
    {
        cout << "B2" << endl;
    }
};
class C : public A
{
public:
    virtual void printC()
    {
        cout << "C" << endl;
    }
};
class C2 : public C
{
    void printC()
    {
        cout << "C2" << endl;
    }
};
 
template<typename T>
T* AddObj();
 
template<>
B* AddObj<B>()
{
    List.push_back(new B); //Как мне быть если я захочу в массив добавить компонент не B, а B2
    return List[List.size() - 1];
}
 
template<>
C* AddObj<C>()
{
    List.push_back(new C); //Точно так же как и с B
    return List[List.size() - 1];
}
Неужели мне придётся каждый наследуемый класс явно специализировать для этой функции?
0
Лучшие ответы (1)
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
04.09.2016, 16:46
Ответы с готовыми решениями:

Ведет ли к инстанцированию определение явной специализации шаблона функции?
сабж ясен из заголовка

Извлечь тип из специализации шаблона
template&lt;class T&gt; class cl { public: T t; cl(){ type t2; } }; cl&lt;cl&lt;int&gt;&gt; v;

Ошибка при специализации шаблона
Пишу: template &lt;&gt; struct Test &lt; int&gt; { Test(int x) :x(x) {} int Cout () { cout &lt;&lt; &quot;Bool&quot;; ...

15
 Аватар для avgoor
1550 / 877 / 179
Регистрация: 05.12.2015
Сообщений: 2,555
04.09.2016, 18:19
C++
1
2
3
4
5
6
template<typename T>
T* AddObj()
{
    List.push_back(new T);
    return &List.back();
}
Не?
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
04.09.2016, 19:58  [ТС]
Нет, совсем не то.
0
2838 / 1647 / 254
Регистрация: 03.12.2007
Сообщений: 4,222
04.09.2016, 20:08
Вроде всё то. Что не так?
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
04.09.2016, 20:29  [ТС]
Ради Бога, простите, я не правильно написал код проблемы. Вот так правильно:
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
#include <iostream>
#include <vector>
using namespace std;
 
class B
{
public:
    virtual void printB()
    {
        cout << "B" << endl;
    }
};
 
class B2 : public B
{
public:
    void printB()
    {
        cout << "B2" << endl;
    }
};
class C
{
public:
    virtual void printC()
    {
        cout << "C" << endl;
    }
};
 
class C2 : public C
{
public:
    void printC()
    {
        cout << "C2" << endl;
    }
};
 
vector<B*> ListB;
vector<C*> ListC;
 
 
template<typename T>
T* AddObj();
 
template<>
B* AddObj<B>()
{
    ListB.push_back(new B); //Как мне быть если я захочу в массив добавить компонент не B, а B2
    return ListB.back();
}
 
template<>
C* AddObj<C>()
{
    ListC.push_back(new C); //Точно так же как и с B
    return ListC.back();
}
int main()
{
    B2* TempB2;
    C2* TempC2;
    TempB2 = AddObj<B2>();
    TempC2 = AddObj<C2>();
 
    TempB2->printB();
    TempC2->printC();
 
    return 0;
}
0
 Аватар для avgoor
1550 / 877 / 179
Регистрация: 05.12.2015
Сообщений: 2,555
04.09.2016, 21:35
Лучший ответ Сообщение было отмечено maks242 как решение

Решение

maks242, Вы еще не уяснили для себя, что глобальные переменные - плохо, а уже в шаблоны лезете...
По теме: можно использовать SFINAE

C++
1
2
3
4
5
6
template<class T>
std::enable_if_t<std::is_base_of<A, T>::value, A*> addObj()
{...ListA}
template<class T>
std::enable_if_t<std::is_base_of<B, T>::value, B*> addObj()
{...ListB}
2
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
05.09.2016, 00:18  [ТС]
avgoor, Интересный вывод, но я создал абстракцию той проблемы, которая у меня на самом деле и чтобы не создавать еще тройку лишних классов я сделал именно так.
0
Эксперт С++
 Аватар для Avazart
8484 / 6151 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
05.09.2016, 00:21
Может стоит все таки разделить и спрятать контейнеры внутрь класса?

C++
1
2
3
4
5
6
7
8
9
template<typename Base>
class Storage
{
        template<typename T> 
        std::shared_ptr<T>  append();
 
    private:
        std::vector<std::shared_ptr<Base> >  objs_;
};
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
05.09.2016, 00:23  [ТС]
Avazart, У меня они спрятаны в другом классе, просто чтобы не мусорить в коде я их вынес.
0
Эксперт С++
 Аватар для Avazart
8484 / 6151 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
05.09.2016, 00:24
Ну тогда проблема не понятна.
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
05.09.2016, 00:27  [ТС]
Avazart, Дело в том, что мне нужно собирать в контейнеры экземпляры разных классов одной функцией. Чтобы так сделать, можно использовать явную специализацию и разных ход поведения для разных иерархий, но проблема в том, что для каждого типа приходиться использовать явную специализацию, а не одну для всей иерархии.
0
Эксперт С++
 Аватар для Avazart
8484 / 6151 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
05.09.2016, 00:30
Цитата Сообщение от maks242 Посмотреть сообщение
Неужели мне придётся каждый наследуемый класс явно специализировать для этой функции?
Т.е. А как вы хотели?
По любому класс нужно как то задекларировать/зарегистрировать. Можно макросом обвернуть что бы короче выглядело.. но суть то не поменяется.

Добавлено через 2 минуты
Цитата Сообщение от maks242 Посмотреть сообщение
Avazart, Дело в том, что мне нужно собирать в контейнеры экземпляры разных классов
Ну так логика где, разные классы - разные контейнеры - а следовательно и ф-ции.
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
05.09.2016, 00:33  [ТС]
Ну, например, я могу записать указатель на дочерний класс в контейнер который хранит указатели на родительский класс, но сделать так в шаблоне не могу, ибо я делаю это для разных иерархий и приходиться явно специализировать каждый тип, хоть и поведение для одной из иерархий одинаковое.
0
 Аватар для avgoor
1550 / 877 / 179
Регистрация: 05.12.2015
Сообщений: 2,555
05.09.2016, 00:56
Цитата Сообщение от maks242 Посмотреть сообщение
хоть и поведение для одной из иерархий одинаковое.
Я ж вам написал, как специализировать шаблон функции для всей иерархии.
0
Эксперт С++
 Аватар для Avazart
8484 / 6151 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
05.09.2016, 01:06
Правильно я понимаю хочется нечто вроде этого:

C++
1
2
3
4
5
6
7
8
9
Storage<BaseX, DerivedX1, DerivedX2, DerivedX3>   StorageX;
 
DerivedX1* dx1 = StorageX.append<DerivedX1>();
DerivedX2* dx2 = StorageX.append<DerivedX2>();
DerivedX3* dx3 = StorageX.append<DerivedX3>();
 
Storage<BaseY, DerivedY1, DerivedY2>   StorageY;
DerivedY1* dy1 = StorageY.append<DerivedY1>();
// ...
0
47 / 21 / 11
Регистрация: 01.11.2013
Сообщений: 255
05.09.2016, 01:12  [ТС]
avgoor, Вам спасибо, я просто объяснял Avazart, в чём состояла моя проблема.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
05.09.2016, 01:12
Помогаю со студенческими работами здесь

О специализации шаблона: почему код компилируется?
Добрый день. Вроде бы, по правилам специализации шаблонов, можно только уточнять поведение шаблонного класса, но нельзя изменять его...

Переопределение или перезагрузка функции
у меня есть класс комплексных чисел. И как можно определить функцию sqrt() что бы она работала с моим классом тоже. Сразу говорю я не хочу...

Возврат объекта шаблонного типа от типа Type из специализации шаблона метода от того же типа
Доброго времени суток, пишу класс содержащий несколько std::set от разных типов, нужно сделать метод возвращающий указатель на нужное...

Multiple definition при специализации функции
Кто может объяснить, почему в этом коде multiple definition для void foo&lt;Test&gt;(Test const&amp;) ? #ifndef TEST_H #define TEST_H class...

Создание специализации шаблонной функции и задача на std::vector
Здравствуйте, подскажите, пожалуйста: 1.В чем ошибка объявления специализации шаблонной функции в header.h template...


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

Или воспользуйтесь поиском по форуму:
16
Ответ Создать тему
Новые блоги и статьи
Советы по крайней бережливости. Внимание, это ОЧЕНЬ длинный пост.
Programma_Boinc 28.12.2025
Советы по крайней бережливости. Внимание, это ОЧЕНЬ длинный пост. Налог на собак: https:/ / **********/ gallery/ V06K53e Финансовый отчет в Excel: https:/ / **********/ gallery/ bKBkQFf Пост отсюда. . .
Кто-нибудь знает, где можно бесплатно получить настольный компьютер или ноутбук? США.
Programma_Boinc 26.12.2025
Нашел на реддите интересную статью под названием Anyone know where to get a free Desktop or Laptop? Ниже её машинный перевод. После долгих разбирательств я наконец-то вернула себе. . .
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка.
Programma_Boinc 23.12.2025
Рецензия / Мнение/ Перевод Нашел на реддите интересную статью под названием The Thinkpad X220 Tablet is the best budget school laptop period . Ниже её машинный перевод. Thinkpad X220 Tablet —. . .
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
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru