![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Быстрое заполнение дин. массива
DelphiLexx © (2007-01-09 09:56:00)У меня есть два массива
APoints: array of TPoint
_Points: array of TPoint
1. Можно ли перенисти все элементы массива APoints в Points не используя цикла?
2. Есть массив
StrokeList: array of DWORD
Который может иметь произвольное число элементов, как мне быстро заполнить его элементы значением числа 2.
Loginov Dmitry (2007-01-10 07:57:00) [1]> А эт чего ?
Ничего. Лопухнулся. См [14].
:)
ors_archangel (2007-01-09 20:01:00) [2]
> _Points := APoints;
> Integer(APoints) := 0;
Помойму всё-таки
_Points := APoints;
хватит, ref-counting сам всё сделает
Сергей М. (2007-01-09 17:30:00) [3]
> Integer(APoints) := 0;
А эт чего ?
Loginov Dmitry (2007-01-09 17:11:00) [4]> У меня есть два массива
>
> APoints: array of TPoint
> _Points: array of TPoint
>
> 1. Можно ли перенисти все элементы массива APoints в Points
> не используя цикла?
_Points := Copy(APoints);
это копирование
А перенос - это:
_Points := APoints;
Integer(APoints) := 0;
Anatoly Podgoretsky (2007-01-09 13:46:00) [5]> () []
А теперь перепиши это без rep stos
Сергей М. (2007-01-09 11:15:00) [6]
> Джо © (09.01.07 10:41) [8]
Тут надо учитывать конкретный CPU)
evvcom (2007-01-09 10:56:00) [7]> [1] Джо © (09.01.07 10:11)
> Move (Pa1[0],Pa2[0],Length(Pa1)*SizeOf(TPoint));
Не пойдет, автор просил без цикла, а внутри Move есть цикл! :)))
Джо (2007-01-09 10:41:00) [8]> [7] Сергей М. © (09.01.07 10:33)
> 2.
>
> Примерно так:
От нечего делать проверил :)
program Project2;
{$APPTYPE CONSOLE}
uses
Windows, SysUtils;
type
TDwordArray = array of Dword;
procedure FillBufferOfDWords(Value: DWord; Buffer: Pointer; Count: Integer);
asm
xchg edx, edi
cld
rep stos dword ptr [edi]
xchg edx, edi
end;
var
Da: TDwordArray;
I: Integer;
Tc: Cardinal;
begin
SetLength (Da,100000000);
//Холостой прогон ;-)
for I := 0 to Length(Da)do
Da[I] := 2;
//1
Tc := GetTickCount;
for I := 0 to Length(Da)do
Da[I] := 2;
WriteLn (GetTickCount-Tc);
//2
Tc := GetTickCount;
FillBufferOfDWords(2,@Da[0],Length(Da));
WriteLn (GetTickCount-Tc);
ReadLn;
end.
У меня оба варианта выполняются 281 тик (+-1) ;)
С включенной оптимизацией.
Сергей М. (2007-01-09 10:33:00) [9]2.
Примерно так:
function FillBufferOfDWords(Value: DWord; Buffer: Pointer; Count: Integer);
asm
xchg edx, edi
cld
rep stos dword ptr [edi]
xchg edx, edi
end;
..
// if Lenght(StrokeList) >0 then //!!!!!
FillBufferOfDWords(2, @StrokeList[0], Lenght(StrokeList));
Джо (2007-01-09 10:22:00) [10]> [5] Сергей М. © (09.01.07 10:21)
>
> > Джо © (09.01.07 10:16) [4]
>
>
> Ну почему же ? "Чистый" rep stosd даст некое преимущество
> по производительности. Хотя вряд ли оно автору надо)
Да можно много напридумывать, я ж не спорю :)
Сергей М. (2007-01-09 10:21:00) [11]
> Джо © (09.01.07 10:16) [4]
Ну почему же ? "Чистый" rep stosd даст некое преимущество по производительности. Хотя вряд ли оно автору надо)
Palladin (2007-01-09 10:16:00) [12]1. можно
SetLength(_Points,Length(APoints)); Move(APoints[0],_Points[0],Length(APoints)*SizeOf(TPoint));
2. хем... можно, но сложно... долго писать...
Джо (2007-01-09 10:16:00) [13]2. Не вижу пути быстрее, чем for I := 0 High(StrokeList) do StrokeList[I] := 2;
Сергей М. (2007-01-09 10:15:00) [14]1.
SetLength(_Points, Length(APoints));
CopyMemory(@_Points[0], @APoints[0], Length(APoints)*SizeOf(TPoint));
2. В цикле.
Джо (2007-01-09 10:11:00) [15]1. Если TPoint это то, о чем я думаю, то:
type
TPointArray = array of TPoint;
var
Pa1,
Pa2: TPointArray;
begin
SetLength (Pa2,Length(Pa1));
Move (Pa1[0],Pa2[0],Length(Pa1)*SizeOf(TPoint));