Модераторы: Daevaorn

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Работа с типами параметров в шаблонной функции, Работа с конкретными типами параметров 
V
    Опции темы
Zerstroer
Дата 26.6.2012, 13:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



Здравствуйте.
Можно ли в шаблонных функциях вызывать не шаблонные функции, работающие с параметрами конкретных типов?
По логике - нельзя, так как компилятор создает копии шаблонной функции при компиляции и, естественно, ругается. Есть ли способ это обойти?
Вот наглядный пример:

Код

#include <cstdlib>
#include <iostream>
#include <string>

using namespace std;

/*Не шаблонная функция, принимающая исключительно string*/
void stringF(string s){    }

/*Шаблонная функция*/
template <typename Anytype>
void templateF(Anytype value, bool b){
    if (b){ 
        /*Функция вызывается только при верности условия b*/
        stringF(value);
    } 
    cout << value << endl;        
}

int main(int argc, char** argv) {
    templateF<string>((string)argv[1], true);
    templateF<int>(atoi(argv[1]), false);
    return 0;
}



--------------------
In silico
PM MAIL ICQ   Вверх
Randajad
Дата 26.6.2012, 13:23 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 295
Регистрация: 15.3.2012

Репутация: 8
Всего: 8



Можно. Почему нельзя?

В данном примере value должно быть типа string, string &, иначе будет ошибка компиляции. Сами подумайте: компилятор ничего не проверяет и передает в stringF то, что вы сунули в шаблонную функцию.

Если же вам нужно сделать шаблонные функции для определенных типов аргументов, то тоже можно.
http://en.cppreference.com/w/cpp/types/enable_if
PM MAIL   Вверх
boostcoder
Дата 26.6.2012, 13:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


pattern`щик
****


Профиль
Группа: Завсегдатай
Сообщений: 5458
Регистрация: 1.4.2010

Репутация: 49
Всего: 110



Цитата(Zerstroer @  26.6.2012,  13:12 Найти цитируемый пост)
Можно ли в шаблонных функциях вызывать не шаблонные функции, работающие с параметрами конкретных типов?

можно.

Цитата(Zerstroer @  26.6.2012,  13:12 Найти цитируемый пост)
компилятор создает копии шаблонной функции при компиляции и, естественно, ругается.

следить за соблюдением conversion должен ты сам.

задачу объясни более развернуто.
PM WWW   Вверх
Zerstroer
Дата 26.6.2012, 13:42 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



Цитата(boostcoder @  26.6.2012,  11:29 Найти цитируемый пост)
задачу объясни более развернуто. 


Объясняю задачу более развернуто:

Есть шаблонная функция, в примере представлена как:

Код

template <typename Anytype>
void templateF(Anytype value, bool b){
    if (b){ 
        stringF(value);
    } 
    cout << value << endl;        
}


Она принимает параметры: 
1. Над которым будет производиться операция. (в примере Anytype value)
2. Параметр, контролирующий, какая именно операция будет производиться (в примере это bool b, в реальной программе я использую перечисление)
По идее, при вызове шаблонной функции, я контролирую conversion за счет передачи кроме типа Anytype, еще и управляющего параметра, но при компилляции нарываюсь на invalid conversion. Не знаю, как это обойти.
Если есть необходимость, могу привести блок кода из реальной программы

C std::enable_if, который предложил Randajad, я не знаком. Мне кажется, что это именно то, что нужно.

Это сообщение отредактировал(а) Zerstroer - 26.6.2012, 13:45


--------------------
In silico
PM MAIL ICQ   Вверх
borisbn
Дата 26.6.2012, 13:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 4875
Регистрация: 6.2.2010
Где: Ростов-на-Дону

Репутация: 22
Всего: 135



специализация в помощь - http://liveworkspace.org/code/2083d4c60654...346db847d7f2929


--------------------
Женщины отличаются от программистов тем, что у них чары состоят из стрингов
PM MAIL Jabber   Вверх
Zerstroer
Дата 26.6.2012, 13:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



borisbn,  smile

Добавлено через 9 минут и 56 секунд
borisbn, ага... Понятно, это получается не особая шаблонная  smile магия  smile, а частная реализация шаблона для конкретного типа? Правильно? И это чревато тем, что будет написано по дополнительной реализации шаблонной функции для каждого "проблемного" типа?






--------------------
In silico
PM MAIL ICQ   Вверх
borisbn
Дата 26.6.2012, 14:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 4875
Регистрация: 6.2.2010
Где: Ростов-на-Дону

Репутация: 22
Всего: 135



Цитата(Zerstroer @  26.6.2012,  13:57 Найти цитируемый пост)
 частная реализация шаблона для конкретного типа? Правильно?

 smile 

Цитата(Zerstroer @  26.6.2012,  13:57 Найти цитируемый пост)
И это чревато тем, что будет написано по дополнительной реализации шаблонной функции для каждого "проблемного" типа?

 smile 

обычно делают именно как я тебе показал - всё общее для всех типов выносят в некую общую функцию (xxx_common или xxx_helper), а в специализации для конкретного типа делают свои черные дела и вызывают эту общую функцию


--------------------
Женщины отличаются от программистов тем, что у них чары состоят из стрингов
PM MAIL Jabber   Вверх
Zerstroer
Дата 26.6.2012, 14:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



borisbn, вообще, приведенное вами решение мне нравится, но у меня есть опасения, что в моем случае, в рабочей программе, оно не совсем уместно по причине того, что слишком объемная шаблонная функция, к тому же внутри неё вызываются другие шаблонные функции.
Вот код из рабочей программы:
Код

   template <typename argumentValueType>
    void checkArgument(argumentValueType argument, argumentsDatatypes datatype){ //Здесь argumentsDatatypes - перечисление
        switch (datatype){ //здесь, в зависимости от datatype - выбираем ветку обработки значения argument
            case SIMPLE: {
                //Обработка не требуется
                break;
            }    
            case RTU_TCP: {
                if (!utils_nmsp::existsInArray<argumentValueType>(MODE_TYPES, argument)) { //вызов шаблонной функции
                    throw ArgumentsAnalyzerException("Wrong mode: " + argument);
                }
                break;
            }
            case PARITY:{
                if (!utils_nmsp::existsInArray<rgumentValueType>(PARITY_TYPES, argument)){ //еще один вызов шаблонной функции
                    throw ArgumentsAnalyzerException("Wrong parity type: " + argument);
                }
                break;
            }  
            case IP4ADDR:{
                if (!utils_nmsp::isIP4ADDR(argument)) {                    //вызов функции, принимающей string
                    throw ArgumentsAnalyzerException("Wrong ip-address: " + argument);
                }
                break;
            }
            case COMPORT:{                    //вызов функции, принимающей string
                if (!utils_nmsp::isCOMPORT(argument)){
                    throw ArgumentsAnalyzerException("Wrong COM-port: " + argument);
                }
                break;
            }
            default: {
                throw ArgumentsAnalyzerException("Unknown argument datatype");
            }
                
        }
        
    }

Мне неудобно будет распиливать это на две шаблонных функции. 

Нахожусь в процессе ознакомления с std::enable_if, предложенным Randajad, она since C++11, надеюсь, получится скомпилировать в gcc 4.4.

Это сообщение отредактировал(а) Zerstroer - 26.6.2012, 14:51


--------------------
In silico
PM MAIL ICQ   Вверх
Randajad
Дата 26.6.2012, 15:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 295
Регистрация: 15.3.2012

Репутация: 8
Всего: 8



А что мешает gcc обновить? smile
4.8 на дворе.
PM MAIL   Вверх
Zerstroer
Дата 26.6.2012, 15:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



Randajad, не подскажете, как с помощью std::enable_if выполнить проверку на принадлежность типа к std::string?


--------------------
In silico
PM MAIL ICQ   Вверх
Zerstroer
Дата 26.6.2012, 16:15 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



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

explicit specialization in non-namespace scope ‘class ChildArgumentsAnalyzer’
template-id ‘checkArgument<std::string>’ in declaration of primary template

В классе нельзя определять 2 шаблонных метода с одинаковым именем?

Это сообщение отредактировал(а) Zerstroer - 26.6.2012, 16:16


--------------------
In silico
PM MAIL ICQ   Вверх
boostcoder
Дата 26.6.2012, 16:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


pattern`щик
****


Профиль
Группа: Завсегдатай
Сообщений: 5458
Регистрация: 1.4.2010

Репутация: 49
Всего: 110



Цитата(Zerstroer @  26.6.2012,  15:48 Найти цитируемый пост)
не подскажете, как с помощью std::enable_if выполнить проверку на принадлежность типа к std::string? 

так: http://en.cppreference.com/w/cpp/types/enable_if

PM WWW   Вверх
Zerstroer
Дата 26.6.2012, 16:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



Цитата(Zerstroer @  26.6.2012,  14:15 Найти цитируемый пост)
В классе нельзя определять 2 шаблонных метода с одинаковым именем?


Наблудил с синтаксисом частной реализации метода.
Сперва хотел, как в примере borisbnа:
Код

template <>
void templateF<string>(string value, bool b){ 

Компилятор ругнулся. В итоге шаблонный метод переопределил таким образом:

Код

template <AnyType = string>
void templateF(string value, bool b){ 


Добавлено через 2 минуты и 26 секунд
Цитата(boostcoder @  26.6.2012,  14:46 Найти цитируемый пост)
так: http://en.cppreference.com/w/cpp/types/enable_if

Или мне не по глазам, или там все таки нету проверки на принадлежность к string.
Там в первую очередь смотрел - не нашел.



--------------------
In silico
PM MAIL ICQ   Вверх
borisbn
Дата 26.6.2012, 17:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 4875
Регистрация: 6.2.2010
Где: Ростов-на-Дону

Репутация: 22
Всего: 135



Цитата(Zerstroer @  26.6.2012,  16:15 Найти цитируемый пост)
в моей рабочей программе шаблон использовался как метод класса

можно использовать параметры шаблона по-умолчанию
http://liveworkspace.org/code/f34fa82a7fad...f9eaae0283471fe

Цитата(Zerstroer @  26.6.2012,  16:46 Найти цитируемый пост)
там все таки нету проверки на принадлежность к string

для этого есть http://en.cppreference.com/w/cpp/types/is_same
Код
template< class T >
void foo( T value, typename std::enable_if< std::is_same< T, std::string >::value >::type * = 0 ) {}
template< class T >
void foo( T value, typename std::enable_if< ! std::is_same< T, std::string >::value >::type * = 0 ) {}




--------------------
Женщины отличаются от программистов тем, что у них чары состоят из стрингов
PM MAIL Jabber   Вверх
Zerstroer
Дата 26.6.2012, 17:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 285
Регистрация: 8.8.2007
Где: Алма-Ата

Репутация: нет
Всего: 3



Цитата(borisbn @  26.6.2012,  15:00 Найти цитируемый пост)
можно использовать параметры шаблона по-умолчанию

Как раз именно так я и поступил.

Каюсь is_same упустил из внимания.

С использованием частной реализации шаблонного метода у меня все получилось. Пробую с использованием enable_if.



--------------------
In silico
PM MAIL ICQ   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0727 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.