LINUX.ORG.RU

Скомпилируется ли это под оффтопиком?

 , template magic,


0

2

Привет. помогите, пожалуйста исправить такую программу - не печатает У кого-нибудь есть в данный момент под рукой msvc? Не могли бы вы посмотреть, скомпилируется ли этот код? Он должен выдать 1005, если всё ок.

Линукс тут при том, что я пишу программу под ним, и временно не имею доступа к окнам.

#include <iostream>
template
<
  int bar(int)
>
int foo()
{
  return bar(1);
}
 
template
<
  int bar(int, int)
>
int foo()
{
  return bar(2,3);
}
 
int bar(int i, int j)
{
  return i+j;
}
 
int bar2(int i)
{
  return 100;
}
 
int main()
{
  std::cout<<foo<bar2>();
  std::cout<<foo<bar>();
}

Ответ на: комментарий от Kalashnikov

Выхлоп

...\bar.cpp(32): error C2440: specialization: невозможно преобразовать "int (__cdecl *)(int)" в "int (__cdecl *const )(int,int)"
          Для преобразования требуется reinterpret_cast, приведение в стиле С или приведение в стиле функции
...bar.cpp(32): error C2973: foo: недопустимый аргумент шаблона "int (__cdecl *)(int)"
          ...\bar.cpp(15): см. объявление "foo"
...\bar.cpp(32): error C2668: foo: неоднозначный вызов перегруженной функции
          ...\bar.cpp(15): может быть "int foo<int bar2(int)>(void)"
          ...\bar.cpp(6): или       "int foo<int bar2(int)>(void)"
          при попытке сопоставить список аргументов "(void)"
...\bar.cpp(33): error C2440: specialization: невозможно преобразовать "int (__cdecl *)(int,int)" в "int (__cdecl *const )(int)"
          Для преобразования требуется reinterpret_cast, приведение в стиле С или приведение в стиле функции
...\bar.cpp(33): error C2973: foo: недопустимый аргумент шаблона "int (__cdecl *)(int,int)"
          ...\bar.cpp(6): см. объявление "foo"
...\bar.cpp(33): error C2668: foo: неоднозначный вызов перегруженной функции
          ...\bar.cpp(15): может быть "int foo<int bar(int,int)>(void)"
          ...\bar.cpp(6): или       "int foo<int bar(int,int)>(void)"
          при попытке сопоставить список аргументов "(void)"
anonymous
()
Ответ на: Выхлоп от anonymous

Всем большое спасибо. Короче, опять тухлая студия обломала все мои хаки.

dmfd
() автор топика
Ответ на: комментарий от Boy_from_Jungle

Ты просто не понимаешь того извращённого удовольствия, которое получаешь от компиляции обмазанного шаблонами кода. Функции высшего порядка на плюсах, применяющиеся в compile time, ня.

Если серьёзно, то производительность требует жертв. Сам не особо рад, что на плюсах писать приходится. А без шаблонов копипаста ехала бы через препроцессор.

dmfd
() автор топика
Ответ на: комментарий от Uter

Это меня не особо интересует, ибо CUDA с ней не дружит.

dmfd
() автор топика
Ответ на: комментарий от dmfd

мне непременно нужен msvc.

Ну так и вали на винфак

anonymous
()

А его не устроит что-нибудь вроде

typedef int BAR1(int);
typedef int BAR2(int, int);
template<const BAR1 *bar> int foo() {return bar(1);}
template<const BAR2 *bar> int foo*() {return bar(2,3);}
int bar(int i, int j) {return i+j;}
int bar2(int i) {return 100;}
int main() {
  std::cout << foo<bar2>() << foo<bar>();
  return 0;
}
?

Кстати, по стандарту, кажется, аргумент шаблона и должен быть константным, так что msvc просто следует стандарту?

Miguel ★★★★★
()
Ответ на: комментарий от Miguel

Я уже по ошибкам вижу (спасибо анону), что нужный фокус никак не пройдет. В msvs, емнип, можно работать с аргументами шаблона так, как я делаю, тут проблема в том, что студия не различает шаблоны с разными сигнатурами.

dmfd
() автор топика
Ответ на: комментарий от Boy_from_Jungle

Вижу, в треде появился человек, у которого многому можно поучиться. Расскажи, пожалуйста, как правильно справляться с комбинаторным взрывом на плюсах, не используя указатели на функции?

dmfd
() автор топика
Ответ на: комментарий от Miguel

Кстати, по стандарту, кажется, аргумент шаблона и должен быть константным, так что msvc просто следует стандарту?

Непонял, это значит, что

pair<int*,int*> не скомпилится и писать надо только pair<const int*,const int*> O_o !

AF ★★★
()
Ответ на: комментарий от dmfd

Я был неправ. Вот так делается:

#include <iostream>
typedef int BAR1(int);
typedef int BAR2(int, int);
int bar(int i, int j) {return i+j;}
int bar2(int i) {return 100;}
template<typename BAR, BAR *bar> struct FOO {static int foo();};
template<BAR1 *bar> struct FOO<BAR1, bar> {static int foo() {return bar(1);}};
template<BAR2 *bar> struct FOO<BAR2, bar> {static int foo() {return bar(2,3);}};
int main() {
    std::cout << FOO<BAR1, bar2>::foo() << FOO<BAR2, bar>::foo();
    std::cin.get();
    return 0;
}
Думаю, можно сделать и так, чтобы оно выводило тип аргумента самостоятельно, но пока не придумал, как.

Miguel ★★★★★
()
Ответ на: комментарий от dmfd

чесно говоря я не особо понял что ты там пилишь, но думаю это можно сделать меньшими костылями. Согласись использовать фичи компилятора не есть гуд. Или я неправ по-твоему?

Boy_from_Jungle ★★★★
()
Ответ на: комментарий от Miguel

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

Но всё равно спасибо, что потратили время.

dmfd
() автор топика
Ответ на: комментарий от Boy_from_Jungle

Скажи, а зачем, по-твоему, я создавал этот тред? Уж не для того ли, чтобы проверить, не является ли данное решение фичей компилятора?

dmfd
() автор топика
Ответ на: комментарий от dmfd

Скажи, а зачем, по-твоему, я создавал этот тред? Уж не для того ли, чтобы проверить, не является ли данное решение фичей компилятора?

Хм, интересно, а кто тогда из компиляторов поступает по стандарту?

O02eg ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.