Параметры по умолчанию для ограничения функций (усилителя)

Следующий код не компилируется. Сообщения об ошибках:

Ошибка 1:

error C3930: 'foo' : no overloaded function has restriction specifiers that are compatible with the ambient context ''

Ошибка 2:

error C2660: 'f1' : function does not take 0 arguments

Ошибка 3:

IntelliSense: amp-restricted function "int foo() restrict(amp)" (declared at line 5) must be called from an amp-restricted function

Программа:

#include <amp.h>
#include <iostream>
using namespace std;

int foo() restrict(amp) { return 5; }

int f1(int x = foo()) restrict(amp) {
  return x;
}

int main()
{
  using namespace concurrency;

  int a[10] = {0};
  array_view<int> av(10, a);

  parallel_for_each(av.extent, [=](index<1> i) restrict(amp) {
    av[i] = f1();
  });

  for(unsigned i=0; i<10; ++i) {
    cout << av[i] << "\n";
  }
  return 0;
}

Как ни странно, когда я удаляю restrict(amp) на foo() и заменяю вызов f1() в лямбде, скажем, на 5, программа компилируется нормально. Итак, каковы правила для вызовов функций в аргументах по умолчанию для функций усилителя?


person keveman    schedule 30.11.2012    source источник
comment
Я столкнулся со странными сообщениями как от GCC, так и от MSVC. Оказывается, у меня был массив из MyStruct, а количество элементов было меньше на единицу: MyStruct s_val[3] = { MyStruct(...), MyStruct(...) };. Ни один из компиляторов не сказал мне, что счет сбит.   -  person jww    schedule 26.10.2017


Ответы (1)


ответ форума MSDN к вопросу.

Семантика выбранных нами аргументов по умолчанию согласуется с общей предпосылкой C++, согласно которой синтаксический анализ программы выполняется за один проход слева направо (несмотря на несколько существенных исключений из этого правила, в первую очередь функции-члены) — поэтому, поскольку спецификатор ограничения читается после объявления параметра функции, любые вызовы функций, расположенные в выражениях аргументов по умолчанию, связаны в соответствии с «внешней» спецификацией ограничения, к лучшему или к худшему. Другими словами, вы читаете программу с самого начала с «активным» ограничением процессора (потому что оно установлено по умолчанию) и переключаетесь на ограничение X для всего, что находится между «restrict(X)» и «}», закрывая соответствующую область.

person keveman    schedule 02.12.2012
comment
Вы, вероятно, должны объяснить это. Мне непонятно, к чему вы клоните (кроме цитирования MSDN). - person jww; 26.10.2017