Как ускорить клонирование массива в С#?
Я работаю над решением проблемы Cult of the Bound Variable.
В части проблемы вы внедряете интерпретатор для "древней" универсальной машины. Я внедрил intrereter для машины, которую они описывают, и теперь я запускаю тестовую программу, которую университет предоставил для ее тестирования.
My С# реализация этого интерпретатора медленно!
Я активировал свою программу в профилировщике ANTS, чтобы увидеть, где происходит замедление, и я вижу, что более 96% моего времени занято операцией "Загрузить программу".
![ANTS Profile Results]()
спецификация этого оператора выглядит следующим образом:
#12. Load Program.
The array identified by the B register is duplicated
and the duplicate shall replace the '0' array,
regardless of size. The execution finger is placed
to indicate the platter of this array that is
described by the offset given in C, where the value
0 denotes the first platter, 1 the second, et
cetera.
The '0' array shall be the most sublime choice for
loading, and shall be handled with the utmost
velocity.
Вот мой код для этого оператора:
case 12: // Load Program
_platters[0] = (UInt32[])_platters[(int)_registers[B]].Clone();
_finger = _registers[C];
break;
Исходный код для всего моего интерпретатора "Универсальная машина" здесь.
Что я могу сделать, чтобы сделать это быстрее? Существуют и другие реализации этого интерпретатора, написанного на языке C, которые значительно ускоряют весь эталон.
Ответы
Ответ 1
Вы можете попробовать Buffer.BlockCopy
, хотя я был бы удивлен, если бы в этом случае имело место огромное различие:
case 12: // Load Program
uint[] src = _platters[(int)_registers[B]];
_platters[0] = new uint[src.Length];
Buffer.BlockCopy(src, 0, _platters[0], 0, src.Length * 4);
_finger = _registers[C];
break;
Ответ 2
Buffer.BlockCopy
promises будет намного быстрее, согласно этот поток MSDN.
Ответ 3
Использовать метод BlockCopy, описанный здесь: http://social.msdn.microsoft.com/Forums/en-US/csharplanguage/thread/42189513-2106-4467-af9a-3b1810509cc8/
Ответ 4
В зависимости от того, как используются два результирующих массива, вы можете использовать модификацию copy-on-write:
Вы не будете использовать массивы напрямую, но с помощью обертки. Чтобы клонировать массив, просто создайте другую оболочку. Если вы попытаетесь написать массив, который используется более чем одной оберткой, вы делаете фактическое клонирование и отделяете обертки.
Ответ 5
Помимо обсуждаемого вопроса, истинная причина, по которой ваши тесты в области производительности настолько низки, что вы должны обрабатывать 0 "с максимальной скоростью", как говорит спецификация;)
По существу, регулярные прыжки выполняются путем нагрузки от 0 до 0. Это очень часто встречается в коде кода. Вы должны полностью избегать клонирования и обновлять только "палец" в этом конкретном случае.