Как я могу достичь максимального параллелизма и использовать максимальный процессор с Parallel.ForEach?
Есть функция C #A(arg1, arg2)
который нужно называть много раз. Чтобы сделать это быстрее, я использую параллельное программирование.
Возьмите пример следующего кода:
long totalCalls = 2000000;
int threads = Environment.ProcessorCount;
ParallelOptions options = new ParallelOptions();
options.MaxDegreeOfParallelism = threads;
Parallel.ForEach(Enumerable.Range(1, threads), options, range =>
{
for (int i = 0; i < total / threads; i++)
{
// init arg1 and arg2
var value = A(arg1, agr2);
// do something with value
}
});
Теперь проблема в том, что это не увеличивается с увеличением количества ядер; например на 8 ядрах он использует 80% процессора, а на 16 ядрах - 40-50% процессора. Я хочу использовать процессор в максимальной степени.
Вы можете предположитьA(arg1, arg2)
внутренне содержит сложные вычисления, но не имеет операций ввода-вывода или сетевых операций, а также не блокирует потоки. Какие есть другие возможности выяснить, какая часть кода делает его неэффективным на 100% параллельным образом?
Я также пытался увеличить степень параллелизма, например,
int threads = Environment.ProcessorCount * 2;
// AND
int threads = Environment.ProcessorCount * 4;
// etc.
Но это не помогло.
Обновление 1 - если я запускаю тот же код, заменивA()
с простой функцией, которая вычисляет простое число, затем использует 100 CPU и хорошо масштабируется. Таким образом, это доказывает, что другой кусок кода является правильным. Теперь проблема может быть в оригинальной функцииA()
, Мне нужен способ обнаружить эту проблему, которая вызывает своего рода последовательность.