Объяснение требований от входных данных к вычислениям на GPU, имеющим сложные результаты

Рассмотрим эту строку кода:

gpuArray(-1)^0.5;

Что приводит к:

ANS =
   0,0000 + 1,0000i

Теперь рассмотрим следующую строку кода:

gpuArray(-1).^0.5;

Что приводит к:

Ошибка при использовании.^ 
POWER: необходимо вернуть сложный результат, но это не поддерживается для реального ввода X и Y на 
ГПУ. Вместо этого используйте POWER(COMPLEX(X), COMPLEX(Y,0)). 

Проблема явно имеет отношение к double -> complex double преобразование на GPU, что не допускается. Действительно, когда я применяю обходной путь (который также упоминается в документации), это решает проблему - но я не понимаю, почему.

Кто-нибудь пролил бы свет на это? Это какое-то ограничение VRAM? Из конкретной карты, которую я использую (у меня GTX 660 с CC 3.0)? Из реализации MATLAB (я использую R2018b)? ОС?

1 ответ

Решение

Есть несколько методов gpuArray что ведут себя так, и причина проста: производительность.

Вполне возможно написать реализацию, например, sqrt он работает на GPU так же, как работает реализация CPU в MATLAB (т.е. вычисляет реальный результат, если не требуется сложный результат - в этом случае возвращает сложный результат). Часть работ уже выполнена - в противном случае gpuArray Метод не знает, когда выдать ошибку. Однако дорогая часть затем перераспределяет (сложный) выход и выполняет операцию снова.

Есть и другие небольшие заметные причуды, связанные с gpuArray и комплексные числа - на GPU все нулевые мнимые части не удаляются, когда реализация CPU MATLAB удаляет их. Например:

>> a = [1i, 2]; gA = gpuArray(a);
>> [isreal(a(2)), isreal(gA(2))]
ans =
  1×2 logical array
   1   0

(Вспоминая, конечно, что MATLAB's isreal функция говорит о хранилище, а не о значениях).

РЕДАКТИРОВАТЬ: Просто понял, что есть конкретные ссылки на документы для функций gpuArray которые ведут себя таким образом.

Другие вопросы по тегам