UPD: вопрос в его первоначальной форме плохо сформулирован, потому что я сильно путаю терминологию (SIMD vs с векторизованными вычислениями) и даю слишком широкий пример, который точно не определяет, в чем проблема; Я голосовал, чтобы закрыть его с «неясно, что вы просите», я связать лучше сформулированный выше вопрос всякий раз, когда он появляетсяКак перевести вычисления в индексной нотации в последовательность операций SIMD в общем случае?
В математике, один, как правило, описывают п-мерный тензор вычислений с использованием индекс обозначения, что будет выглядеть примерно так:
A[i,j,k] = B[k,j] + C[d[k],i,B[k,j]] + d[k]*f[j] // for 0<i<N, 0<j<M, 0<k<K
, но если мы хотим использовать любую библиотеку SIMD эффективно распараллелить, что вычисление (и воспользоваться линейно-алгебраические магии), мы должны выразить его с помощью примитивов из BLAS
, numpy
, tensorflow
, OpenCL
, ...
, что часто довольно сложно.
Выражения в [Эйнштейна обозначений] [1], как A_ijk*B_kj
, как правило, решаются с помощью [np.einsum
] [2] (с помощью tensordot
, sum
и transpose
, я полагаю?). Суммирование и другие элементарные операции также хорошо, «умное» индексирование довольно сложно, хотя (особенно, если индекс появляется больше, чем один раз в выражении).
Интересно, существуют ли какие-либо языковые агностические библиотеки, которые принимают выражение в определенной форме (скажем, форму выше) и переводит его в некоторый Intermediate Representation
, который может быть эффективно выполнен с использованием существующих библиотек линейных алгебр?
Есть библиотеки, которые пытаются распараллелить вычисление цикла (пользователь API обычно выглядит #pragma
в C++ или @numba.jit
в Python), но я спрашиваю о немногих другом деле: перевести abritary выражения в форме выше, в конечную последовательность SIMD команды, как поэлементного-OPS, matvecs, tensordots и т.д.
Если нет языка агностик решения еще, я лично заинтересован в Numpy вычислениях :)
Я понял, что не так с вопросом? Ответ «нет, и это невозможно, потому что X» тоже является приемлемым ответом :) Я был бы очень доволен, если бы существовал такой алгоритм библиотеки (и я не один). Я переформулировал вопрос, если сама форма вопроса является уродливой. –
Можете ли вы написать цикл в C или какой-то псевдокод, который четко выражает тип вычислений, который вы хотите векторизовать? Я не уверен, что понимаю вашу букву '{}'. Если это что-то похожее на матрицу, то, да, перенос одного из входов часто очень полезен, поэтому данные, необходимые для последовательных результатов, хранятся в обоих источниках одновременно. –
@PeterCordes благодарим вас за комментарий! Я согласен, я обновил вопрос, нотация выглядит менее двусмысленной? –