0 / 0 / 0
Регистрация: 20.05.2018
Сообщений: 17
1

Специализация шаблона не подходит ни к одному объявленному шаблону

04.07.2018, 14:01. Показов 953. Ответов 6
Метки нет (Все метки)

Задание:
Напишите шаблонную функцию maxn(), которая принимает в качестве аргумента массив элементов типа T и целое число, представляющее количество элементов в массиве, а возвращает элемент с наибольшим значением. Протестируйте ее работу в программе, которая использует этот шаблон с массивом из шести значений int и массивом из четырёх значений double. Программа также должна включать специализацию, которая использует массив указателей на char в качестве первого аргумента и количество указателей - в качестве второго, а затем возвращает адрес самой длинной строки. Если имеется более одной строки наибольшей длинны, функция должна вернуть адрес первой из них. Протестируйте специализацию на массиве из пяти указателей на строки.
Код

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
#include <iostream>
#include <cstring>
#include <windows.h>
 
template <typename T>
T maxn(T * arr, const int n);
template <>
char* maxn<char*>(char * arr, const int n);
int main()
{
    using namespace std;
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    int int_num[6] = {1, 5, 85, 34, 165, 48};                                           //массив int
    double double_num[4] = {1.54, 45.98, 25.78, 34.6};                                  //массив double
    char strings[5][15] = {"Мастер", "Новичек", "Ученик", "Адепт", "Легендарный"};      //двумерный массив строк
    char *char_pointer[5];                                                              //указатели на строки
    for (int i = 0; i < 5; i++)
        char_pointer[i] = &strings[i][0];
    int max_int = maxn(int_num, 6);
    double max_double = maxn(double_num, 4);
    char * diff = maxn(char_pointer, 5);
    cout << "Наибольшее целое число = " << max_int << endl;
    cout << "Наибольше число с плавающей точкой = " << max_double << endl;
    cout << "Самая длинная строка = " << *diff << endl;
    return 0;
}
template <typename T>
T maxn(T * arr, int n)
{
    T max = 0;
    for (int i = 0; i < n; i++)
        //если значение arr[i] больше max присваиваем max значение arr[i] иначе без изменений
        max = arr[i] > max ? arr[i] : max;
    return max;
}
template <>
char* maxn(char * arr, const int n)
{
    char max[15];
    for (int i = 0; i < n-1; i++)
    {
        if(strlen(arr[i]) > strlen(arr[i+1]))       //если длина первой строки i строки больше строки i+1
            strcpy(max, arr[i]);                    //то копируем в max i строку
        else                                        //иначе
            strcpy(max, arr[i+1]);                  //копируем в max i+1 строку
    }                                               //в конце цикла max равна максимальной строке
    return max;
}

ошибка
||=== Build: Debug in 8.6 (compiler: GNU GCC Compiler) ===|
D:\C++\8.6\main.cpp|8|error: template-id 'maxn<char*>' for 'char* maxn(char*, int)' does not match any template declaration|
D:\C++\8.6\main.cpp|38|error: template-id 'maxn<>' for 'char* maxn(char*, int)' does not match any template declaration|
||=== Build failed: 2 error(s), 0 warning(s) (0 minute(s), 0 second(s)) ===|

Подскажите как изменить специализацию, чтобы работала и в чем ошибка? или тут в другом проблема?
Вложения, ожидающие проверки
Тип файла: jpg задание 8.6.jpg
__________________
Помощь в написании контрольных, курсовых и дипломных работ, диссертаций здесь
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
04.07.2018, 14:01
Ответы с готовыми решениями:

Специализация шаблона
Здравствуйте! Задача: Создайте шаблонную функцию maxn(), которая принимает в качестве...

Специализация шаблона
Всем доброго вечера! Возникает непонятная ошибка при создании специализации родового класса cl. В...

Специализация шаблона
Привет, у меня есть вот такой шаблон дерева: template &lt;typename T = int&gt; class Tree{ ...

специализация шаблона
начал разбираться с шаблонами. если есть структура, и одна функция именно с int должна работать по...

6
Модератор
Эксперт С++
12099 / 9772 / 5908
Регистрация: 18.12.2011
Сообщений: 26,235
04.07.2018, 14:14 2
В суть не вникал, но специализация будет такая
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
template <char>
char* maxn(char* arr, const int n)
{
    char* max=new char[16];
    for (int i = 0; i < n-1; i++)
    {
        if(strlen(arr[i]) > strlen(arr[i+1]))       //если длина первой строки i строки больше строки i+1
            strcpy(max, arr[i]);                    //то копируем в max i строку
        else                                        //иначе
            strcpy(max, arr[i+1]);                  //копируем в max i+1 строку
    }                                               //в конце цикла max равна максимальной строке
    return max;
}
но arr[i] - это отдельный символ, а не строка
0
0 / 0 / 0
Регистрация: 20.05.2018
Сообщений: 17
04.07.2018, 14:49  [ТС] 3
Цитата Сообщение от zss Посмотреть сообщение
В суть не вникал, но специализация будет такая
Спасибо, понял в чем дело. Вопрос, в коде выше строка
C++
1
char * diff = maxn(char_pointer, 5);
оказывается принимает только один символ и отображается дальше тоже первый символ строки только.
Я переделал на
C++
1
char * diff[16] = {maxn(char_pointer, 5)};
сначала сделал без фигурных скобок и получил ошибку.
Вопрос, как такой код работает? То есть как он инициализирует массив хотя получает только один символ и почему он не может обойтись без фигурных скобок?
Я уже запутался с этими массивами. Вроде же указатель на первый элемент массива - это указатель на весь массив, но почему то возврат указателя на массив возвращает только первый символ. И инициализация не совсем с этими фигурными скобками понятна. Как работает присваивание в этих скобках, точнее каким образом инициализируется каждый элемент массива?
Извините, все запутано, но что то бардак в голове уже)

Добавлено через 14 минут
Цитата Сообщение от zss Посмотреть сообщение
В суть не вникал, но специализация будет такая
Стоп стоп, первый не редактированный вариант ваш заработал успешно
Кликните здесь для просмотра всего текста
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
#include <iostream>
#include <cstring>
#include <windows.h>
 
template <typename T>
T maxn(T * arr, const int n);
template <>
char* maxn<char*>(char ** arr, const int n);
int main()
{
    using namespace std;
    SetConsoleCP(1251);
    SetConsoleOutputCP(1251);
    int int_num[6] = {1, 5, 85, 34, 165, 48};                                           //массив int
    double double_num[4] = {1.54, 45.98, 25.78, 34.6};                                  //массив double
    char strings[5][15] = {"Мастер", "Новичек", "Ученик", "Адепт", "Легендарный"};      //двумерный массив строк
    char *char_pointer[5];                                                              //указатели на строки
    for (int i = 0; i < 5; i++)
        char_pointer[i] = &strings[i][0];
    int max_int = maxn(int_num, 6);
    double max_double = maxn(double_num, 4);
    char * diff[16] = {maxn(char_pointer, 5)};
    cout << "Наибольшее целое число = " << max_int << endl;
    cout << "Наибольше число с плавающей точкой = " << max_double << endl;
    cout << "Самая длинная строка = " << *diff << endl;
    return 0;
}
template <typename T>
T maxn(T * arr, int n)
{
    T max = 0;
    for (int i = 0; i < n; i++)
        //если значение arr[i] больше max присваиваем max значение arr[i] иначе без изменений
        max = arr[i] > max ? arr[i] : max;
    return max;
}
template <>
char* maxn(char ** arr, const int n)
{
    char* max = new char[16];
    for (int i = 0; i < n-1; i++)
    {
        if(strlen(arr[i]) > strlen(arr[i+1]))       //если длина первой строки i строки больше строки i+1
            strcpy(max, arr[i]);                    //то копируем в max i строку
        else                                        //иначе
            strcpy(max, arr[i+1]);                  //копируем в max i+1 строку
    }                                               //в конце цикла max равна максимальной строке
    return max;
}

вот заработавший код. А тот код что вы отредактировали как раз и не работал у меня. Нужно было именно arr**.
0
Модератор
Эксперт С++
12099 / 9772 / 5908
Регистрация: 18.12.2011
Сообщений: 26,235
04.07.2018, 15:09 4
но тогда это не специализация, а перегруженная функция с другим типом параметра
1
Don't worry, be happy
17758 / 10526 / 2030
Регистрация: 27.09.2012
Сообщений: 26,502
Записей в блоге: 1
04.07.2018, 15:22 5
Цитата Сообщение от zss Посмотреть сообщение
но специализация будет такая
Это не специализация, а обычный шаблон с параметром не-типом.
1
Форумчанин
Эксперт CЭксперт С++
8190 / 5040 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
04.07.2018, 16:03 6
Лучший ответ Сообщение было отмечено HasTig как решение

Решение

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
template <typename T>
T maxn(T * arr, int n)
{
    if(n == 0)
    {
        return T();
    }
    T max = arr[0];
    for (int i = 1; i < n; i++)
    {
        if(arr[i] > max)
        {
            max = arr[i];
        }
    }
    return max;
}
template <>
char * maxn(char ** arr, const int n)
{
    if(n == 0)
    {
        return "";
    }
    char * max = arr[0];
    for (int i = 1; i < n; i++)
    {
        if(strlen(arr[i]) > strlen(max))
        {
            max = arr[i];
        }
    }
    return max;
}
1
0 / 0 / 0
Регистрация: 20.05.2018
Сообщений: 17
05.07.2018, 22:03  [ТС] 7
Спасибо всем разобрался немного)
Цитата Сообщение от zss Посмотреть сообщение
но тогда это не специализация, а перегруженная функция с другим типом параметра
Все таки это специализация
Как я понял в шаблоне
C++
1
2
template <typename T>
T maxn(T * arr, const int n);                //принимаем массив (например int) возвращаем просто значение int
а специализация
C++
1
2
template <>
char* maxn<char*>(char ** arr, const int n);            //принимает массив массивов возвращает просто массив
Как я понял именно поэтому
C++
1
char* maxn<char*>(char * arr, const int n);
выдавал ошибку, потому что в шаблоне уже есть указатель в принимаемом значении, но возвращается не указатель - значит в специализации, где возвращается указатель, приниматься должен указатель на указатель. Поправьте если не прав, пожалуйста
0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
05.07.2018, 22:03
Помогаю со студенческими работами здесь

специализация шаблона
Добрый день! Хотелось бы сделать шаблонную функцию, у которой будет различная реализация в...

Специализация шаблона
Пытаюсь специализировать шаблон для типа float, но не получается. В чем проблема? Компилятор:...

Явная специализация шаблона
Здравствуйте. Не совсем разобрася с сабжем. Например, если есть кусочек кода: template &lt;typename...

Специализация шаблона функции
Допустим у нас имеется шаблон функции такой, в угловых скобках которого содержатся как типовые...


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

Или воспользуйтесь поиском по форуму:
7
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2022, CyberForum.ru