Высокая производительность
.NET
Алгоритмы
C#
Комментарии 22
+1
Я думаю, что замена многомерных массивов double[x,y] на одномерные double[x*y] даст неплохой прирост производительности. Не в 30 раз конечно но даст.
0

Далеко не факт.
Я не работал с C#, но на Java (понимаю что языки совершенно разные) приходилось иногда делать расчеты в многомерных массивах.
Очень и очень редко переход с n-мерных массивов к одномерному приводили к ускорению выполнения. В особо успешных случаях ускорение было, но на грани погрешности.
Смею предположить, что иногда компилятор или VM догадываются о том, что делает код и сами разворачивают его в один цикл.
Вполне возможно, что C# способен на такое.


Вообще лучше всего проверить на практике. У меня жаль под рукой C# нет

+1
>Вполне возможно, что C# способен на такое.
Не не способен. Печаль в том что в .NET хорошо оптимизированы одномерные массивы, и вообще никак многомерные. К примеру доступ к элементу в одномерном массиве это IL opcode ld.elem, в многомерном это вызов метода на классе Array, который потом транслируется в кишки CLR. Так что разница может быть существенной.
0
Думаю вы правы, что это ускорило бы процесс. Только это потребовало бы уже гораздо больше усилий, чтобы перепахать всю внутреннюю логику на поддержку этого.
-2
Имеет смысл для маленьких матриц, которые полностью влезут в кэш. Для больших матриц принципиальной разницы не будет ни на каком ЯП.
0
Здравый смысл подсказывает что многомерные (которые T[,] а не jugged вариант T[][]) массивы внутри устроены как обычные одномерные с трансляцией индексов вида
(i, j) -> i * dim(1) + j
(возможно с выравниванием), и вряд ли дадут значительное ускорение при ручном перепиливании.
Могут ли товарищи знакомые с кишками компилятора подтвердить или опровергнуть эту догадку?
0
Проверил, простое заполнение небольшого двумерного массива x,y проходит несколько медленнее, чем одномерного x*y.

int x, y, z;
int i, j, k;

x = 100;
y = 10;
z = 10000;

double[,] a = new double[x, y];
double[] b = new double[x * y];

Stopwatch stA = new Stopwatch();
stA.Start();

for (k = 0; k < z; k++)
for (i = 0; i < x; i++)
for (j = 0; j < y; j++)
a[i, j] = i * k;

stA.Stop();

Stopwatch stB = new Stopwatch();
stB.Start();

for (k = 0; k < z; k++)
for (i = 0; i < x * y; i++)
b[i] = i * k;

stB.Stop();

Results:

stA.Elapsed.Ticks = 531087
stB.Elapsed.Ticks = 390716
+1
Интересно было бы про саму библиотеку прочесть в примерах. А если в двух словах, что в ней можно делать?
0
Кроме классических сетей (с реализацией обучения, отжига и т.д.) есть сети Хопфилда, самоорганизующиеся карты Кохонена. Вот тут куча примеров использования:

https://github.com/jeffheaton/jeffheaton-book-code/tree/master/CSIntroNeuralNetworkEdition2
+1
Здорово получилось, конечно. Но что-то мне подсказывает, что переход на GPU обеспечит ускорение еще на порядок :)
0
Да, GPU показывает изумительные результаты. Я пробовал делать расчеты на GPU, оказалось там очень большие затраты на ввод вывод данных (вплоть до проигрыша CPU в сумме). Специфика моего приложения в том, что обмен данными очень интенсивный, такой что смысла юзать GPU не увидел.
+1
Прежде еще можно задействовать SIMD (System.Numerics.Vectors) и переделать double на float.
+1
Этот код у его автора на гитхабе лежит. Почему бы не запилить туда коммит для более всеобщей борьбы с энтропией?
+1
«и глядя на загрузку CPU по 50-60% по телу бежал неприятный холодок — кто-то халтурит!» :)
0
Да это к счастью не проблема, загрузить проц весьма легко увеличив кол-во параллельно выполняющихся потоков в 1,5-2 раза, данный пример был для сравнимости результатов при одинаковом коде приложения (менялась только библиотека).
0
А статья для которой версии библиотеки? GetCol в текущей есть, но ни разу не используется. DotProduct вызывается в одном месте, не очень часто используемом. Можно попробовать сравнить с результатом, при использовании последней версии.
0
Интересно, какие задачи решаете с помощью этих сетей?
И какие максимальные размеры сеток (сколько слоев)
и входных таблиц (столбцов, строк) получается обрабатывать в этой библиотеке?
0
Проект — макроэкономическое моделирование. Надеюсь вскоре будут результаты достойные публикации. Размер сеток на данный момент 200x70x15 (три слоя).
0
Продолжаю любопытствовать. А топология которая используется? MLP?
0
Да, собственно топологии еще не перебирал (даже кол-во слоев не пробовал менять). Пока занимаюсь отладкой общей логики и функциональной обвязки (распределение вычислений по сети на несколько машин и агрегация результатов).
Только полноправные пользователи могут оставлять комментарии.  , пожалуйста.