Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2002.09.02;
Скачать: [xml.tar.bz2];

Вниз

Избавление от нулей в строчке???   Найти похожие ветки 

 
CCCatch   (2002-08-21 12:40) [0]

Как удалить все имеющиеся нули из Edit1??


 
CCCatch   (2002-08-21 12:46) [1]

Причём удалить нужно только нули, а всё остальное оставить


 
Anatoly Podgoretsky   (2002-08-21 12:49) [2]

Процедура Delete в цикле


 
Alx2   (2002-08-21 12:51) [3]

>Anatoly Podgoretsky © (21.08.02 12:49)
сложность порядка O(n^2) вместо O(n).


 
Dmitriy Polskoy   (2002-08-21 12:53) [4]

procedure TForm1.Button1Click(Sender: TObject);
var
S: string;
begin
S := "000123.5";
while Pos("0", S) > 0 do
delete(s,Pos("0", S),1);
ShowMessage(s);
end;


 
Alx2   (2002-08-21 13:00) [5]

>Dmitriy Polskoy © (21.08.02 12:53)
Очень медленно будет работать:(
Хотя может я и зря: нужна ли здесь скорость? :)


 
Jeer   (2002-08-21 13:01) [6]

S := StringReplace(S, "0", "rfReplaceAll" );


 
Anatoly Podgoretsky   (2002-08-21 13:02) [7]

Alx2 © (21.08.02 12:51)
сложность порядка O(n^2) вместо O(n).

Это почему же, я предлагаю сделать это за один проход


 
Alx2   (2002-08-21 13:03) [8]

>Anatoly Podgoretsky © (21.08.02 13:02)
Внутри Delete тоже будет все перетаскиваться за O(n). Отсюда квадратичность.


 
McSimm   (2002-08-21 13:13) [9]

>Alx2 © (21.08.02 13:03)
Внутри Delete тоже будет все перетаскиваться за O(n)


не будет. Обычный move() будет.

>Jeer © (21.08.02 13:01)
чуть подправлю:
S := StringReplace(S, "0", "", [rfReplaceAll]);


 
Alx2   (2002-08-21 13:16) [10]

>McSimm © (21.08.02 13:13)
>не будет. Обычный move() будет.
Блин, а третьим параметром в move что идет?!


 
McSimm   (2002-08-21 13:32) [11]

Alx2 © (21.08.02 13:16)
а третьим параметром в move что идет?!


А, в этом смысле :)
Ну, считать rep movsb за цикл это несколько жестко, хотя принципиально ты прав.

Однако, меня интересует твой алгоритм. Если в цикле
if S1[i] <> "0" then S2 := S2 + S1[i],
то IMHO это намного медленнее


 
Alx2   (2002-08-21 13:39) [12]

>McSimm © (21.08.02 13:32)
>Ну, считать rep movsb за цикл это несколько жестко, хотя
>принципиально ты прав.

Самый настоящий цикл. И не намного быстрее цикла на базе явных условных переходов, а на некоторых процессорах даже и медленнее.



 
Alx2   (2002-08-21 13:49) [13]

>McSimm © (21.08.02 13:32)

В S1 - строка без нулей.
Var S, S1 : String;
k,l : integer;
begin
S := "000sdfdss00000001000000фыаф001100fgh000010";
setLength(S1,Length(S));
l := 0;
for k := 1 to Length(S) do
if S[k]<>"0" then
begin
inc(l);
S1[l] := S[k]
end;
SetLength(S1,l);
ShowMessage(S1);
end;


 
Alx2   (2002-08-21 14:24) [14]

>McSimm © (21.08.02 13:32)
>if S1[i] <> "0" then S2 := S2 + S1[i],
>то IMHO это намного медленнее
Того же порядка: O(n^2)


 
lak_b   (2002-08-21 14:32) [15]

не... ну запарили с такими вопросами... можд ещё компонент такой забацать?! вот они - программисты... ладнаб ещё спросил, какой самый быстрый способ сабжа...


 
McSimm   (2002-08-21 14:33) [16]

>Alx2 ©
Согласен, твой вариант быстрее. Но, как ты уже сам подметил, это не тот случай где нужна подобная оптимизация :)

Хотя, ты наверное будешь удивлен, для некоторых ситуаций следующая функция работает быстрее :)

function A2(const S: String): String;
var i: Integer;
begin
Result := S;
for i := Length(Result) downto 1 do
if Result[i] = "0" then Delete(Result, i, 1)
end;


 
McSimm   (2002-08-21 14:41) [17]

>lak_b © (21.08.02 14:32)

:) Не придирайся, ну не спросил, пусть самим интересно, какая разница ?

>Alx2 ©
например на таком тесте:
for I := 1 to 100000 do A2(IntToStr(I))


 
Alx2   (2002-08-21 15:07) [18]

>lak_b © (21.08.02 14:32)
Не мешай извращаться :)

>McSimm © (21.08.02 14:41)
При таком подходе это все-таки быстрее: :)

function a3(const S: string): string;
var k, l: integer;
begin
Result := S;
l := pos("0", Result);
if l > 0 then
begin
for k := l + 1 to Length(Result) do
if Result[k] <> "0" then
begin
Result[l] := Result[k];
inc(l);
end;
SetLength(Result, l - 1);
end;
end;




 
McSimm   (2002-08-21 15:20) [19]

Соревнования !
Дуель !
:)

procedure TForm1.Button1Click(Sender: TObject);
var I: Integer;
D2, D3: TDateTime;
begin
D2 := Now;
for I := 1 to 100000 do
A2(IntToStr(I));
D2 := Now - D2;
D3 := Now;
for I := 1 to 100000 do
A3(IntToStr(I));
D3 := Now - D3;
Memo1.Lines.Add("A2 = "+FloatToStr(D2));
Memo1.Lines.Add("A3 = "+FloatToStr(D3));
Memo1.Lines.Add("A2 - A3 = "+FloatToStr(D2-D3));
if D2 < D3 then ShowMessage("АГА :)")
else ShowMessage("УГУ :(")
end;

Ага !


 
Alx2   (2002-08-21 15:27) [20]

Memo1:
A2 = 1.62037031259388E-6
A3 = 1.50463165482506E-6
A2 - A3 = 1.15738657768816E-7

УГУ :(

-------------
Ха-ха!

???


 
Alx2   (2002-08-21 15:34) [21]

Вдесятеро больший цикл:
Memo1
A2 = 1.73842563526705E-5
A3 = 1.69328704942018E-5
A2 - A3 = 4.51385858468711E-7

Снова мой алгоритм победил.


 
McSimm   (2002-08-21 16:09) [22]

>Alx2 © (21.08.02 15:27)
A2 = 2,16435000766069E-6
A3 = 2,17592605622485E-6
A2 - A3 = -1,15760485641658E-8
Предлагаю ничью и завязываем с этой темой :)

>Вдесятеро больший цикл
Это уже другая ситуация:
"для некоторых ситуаций следующая функция работает быстрее"



 
Alx2   (2002-08-21 16:14) [23]

>McSimm © (21.08.02 16:09)
Ничья - нечестно :)
В предлагшаемой оценке времени есть случайные колебания. Посему время испытания должно быть достаточным, чтобы достаточно уменьшить влияние помех.


 
Ученик   (2002-08-21 16:20) [24]

A2 = 1.44675868796185E-6
A3 = 1.44675868796185E-6
A2 - A3 = 0


 
Толик   (2002-08-21 16:29) [25]

Не очень понятно о чём спор? Т.к. последовательность не сортированная, то кроме последовательного перебора здесь ничего не придумать. Весь вопрос сводится к тому, что "очищенные" данные надо не сдвигать, а переносить предварительно выделенное место.


 
McSimm   (2002-08-21 16:56) [26]

Толик © (21.08.02 16:29)

Не очень понятно о чём спор?

На самом деле абсолютно ни о чем :)


 
Alx2   (2002-08-21 17:02) [27]


procedure UniversalDelete(Var Arr; ArrSize : Integer; ElemSize, DeleteIdx : Integer);
Var
Source, Dest : Integer;
DummyArr : array of char absolute Arr;
Begin
ArrSize := ArrSize * ElemSize;
Source := (DeleteIdx+1)*ElemSize;
Dest := Source-ElemSize;
Move(DummyArr[Source],DummyArr[Dest],ArrSize-(DeleteIdx+1)*ElemSize);
SetLength(DummyArr,ArrSize div ElemSize - 1);
End;


Пример использования:
Var
SS : array of integer;
begin
setlength(SS,10);

for k := 0 to 9 do SS[k] := (k);

UniversalDelete(SS,Length(SS),SizeOf(SS[0]),2);
Первый параметр - массив.
Второй - количество элементов в нем
Третий - размер одного элемента массива
Четвертый - номер удаляемого элемента (считая с нуля).

PS.
Будь осторожен. Написано в черновую, хоть глюков пока не замечено (но потенциально может испортить работу менеджера памяти - надо проверить)


 
Alx2   (2002-08-21 17:03) [28]

>Alx2 © (21.08.02 17:02)
Ребята, сорри!
Веткой ошибся.


 
Alx2   (2002-08-21 17:14) [29]

>Толик © (21.08.02 16:29)
Так... пальцы размять, отдохнуть...


 
Anatoly Podgoretsky   (2002-08-21 17:33) [30]

Не вижу смысла в оптимизации, речь идет об Edit.Text не те размеры, даже цикл while Pos("0", ) будет слишком быстрый


 
Ученик   (2002-08-21 17:47) [31]

>CCCatch (21.08.02 12:40)
Так может просто не давать их вводить ? :)


 
McSimm   (2002-08-21 17:56) [32]

>Anatoly Podgoretsky © (21.08.02 17:33)
Разумеется. Весь этот спор шутки ради.
Мы уже закончили.


 
Alx2   (2002-08-22 08:28) [33]

>Anatoly Podgoretsky © (21.08.02 17:33)
>Не вижу смысла в оптимизации, речь идет об Edit.Text не те
>размеры, даже цикл while Pos("0", ) будет слишком быстрый

Да, конечно. В этом частном случае.
Но когда, например, в UBPFD появляются "кривые" в этом плане примеры, невольно задумаешся откуда же растут ноги....



Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2002.09.02;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.52 MB
Время: 0.009 c
14-3602
Bboy
2002-08-07 15:19
2002.09.02
Очень нужна программа


1-3515
AlexBeliy
2002-08-21 15:11
2002.09.02
Создание новой формы


3-3234
Ренат
2002-08-08 09:28
2002.09.02
Ошибки при открытии таблиц


3-3248
Dino Ray
2002-08-12 01:03
2002.09.02
IDX поля типа CHAR?


4-3670
mxsbnet
2002-07-02 10:19
2002.09.02
Мигание окошка в панели задач





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский