![]() |
|
|
|||||||
| Регистрация | << Правила форума >> | FAQ | Пользователи | Календарь | Поиск | Сообщения за сегодня | Все разделы прочитаны |
![]() |
|
|
Опции темы | Поиск в этой теме | Опции просмотра |
|
|
|
#1
|
|||
|
|||
|
Есть список в listBox с наименованием параметров.
типо Код:
Право Лево Вверх В низ Вперёд Назад ... Но сразу все они не используются. В Мемо может оказаться один, а других 5-10 не будет. В следующий раз наоборот. Есть мемо с кучей строк типа Код:
------ ##### ------ Право --- 15 % Лево --- 21 % Право --- 21 % Вперёд --- 0 % ------ №№№№ ------ ------******* ------ ------ №№№№ ------ Вверх --- 2 % Право --- 4 % Назад --- 0 % Лево --- 6 % В низ --- 5 % Право --- 0 % Как это дело спарсить что б в результате получилось так: Код:
------ ##### ------ Право --- 15 % Лево --- 21 % Право --- 21 % Вперёд --- 1 % ------ №№№№ ------ ------******* ------ ------ №№№№ ------ Вверх --- 2,2 % Право --- 4 % Назад --- 0 % Лево --- 6 % В низ --- 5 % Право --- 0 % ------ Итог: ----- Право --- 40 % Лево --- 27 % Вперёд --- 1 % Вверх --- 2,2 % В низ --- 5 % Тоесть что б все проценты с одинаковыми параметрами суммировались и в итог попали только параметры с положительным процентом. Проценты могут быть числом с запятой. Итог надо записать в конец мемо. Думаю надо сделать типо двух циклов. Что б первый подставлял в переменную значение строки из списка, Второй пробегал по всему Мемо и искал строки с этим значением. Если б делал одно значение, было б типа такого: Код:
{################## Функция парсинга ################}
function Pars(T_, ForS, _T: string): string;
var a, b:integer;
begin
Result := '';
if (T_='') or (ForS='') or (_T='') then Exit;
a:=Pos(T_, ForS);
if a=0 then Exit else a:=a+Length(T_);
ForS:=Copy(ForS, a, Length(ForS)-a+1);
b:=Pos(_T, ForS);
if b>0 then
Result:=Copy(ForS, 1, b - 1);
end;
{----------------------------------------------------}
procedure TForm1.Button1Click(Sender: TObject);
var
I:integer;
S: string;
bonus1:real; // Право
begin
S:=memo1.Text;
For I:=0 to Memo1.Lines.Count-1 do
begin
If pos('Право --- ',S)<>0 then
Begin
bonus1:=bonus1+StrToFloat(pars('Право ---', s, ' %'));
End;
End;
memo1.lines.Add('');
memo1.lines.Add('--- Итог: ---');
memo1.lines.Add('');
memo1.lines.Add('Право --- '+ FloatToStr(bonus1)+' %');
end;Но в listBox 30 значений лежит. Можно конечно 30 проверок налепить, но хочется по нормальному сделать в цикле. Наверно надо как то через два цикла делать. Что б первый подставлял из listBox значения, а второй пробегался по всему Мемо и парсил то что нужно. Что б вместо Код:
...
If pos('Право --- ',S)<>0 then ...Код:
... If pos(listBox1.Items.Strings[b]+' --- ',S)<>0 then ... И ещё вопрос: Есть несколько переменных, a1, a1, a2, a3, a4, a5:string; можно ли им присваивать индексы в цикле ? что б типа такого получилось: Var i:integer; a1, a1, a2, a3, a4, a5:string; Begin For i:=0 to Memo1.Lines.Count-1 do begin If pos('123',Memo1.Lines.Strings[i])<>0 then Begin a[i]:=Memo1.Lines.Strings[i]; end; end; end; Спасибо. Последний раз редактировалось TEKTON, 26.07.2018 в 21:41. |
|
#2
|
|||
|
|||
|
Заводишь массив для подсчета значения параметра.
Далее ползешь по мемо, для каждой строки выделяешь нужный параметр и суммируешь в массиве. Далее просто вывод. Как-то так: Код:
var
P : Array Of Double;
I, pIdx : Integer;
pName : String;
pVal : Double;
begin
SetLength(P,ListBox1.Items.Count);
For I := Low(P) To High(P) Do P[i] := 0; // just in case
For I := 0 To Memo1.Lines.Count-1 Do
Begin
ExtractParamNameFromLine(Memo1.Lines[i],pName,pVal);
If pName <> '' Then
Begin
pIdx := ListBox1.Items.IndexOf(pName);
If pIdx > -1 Then P[pIdx] := P[pIdx] + pVal;
End;
End;
// Print to memo
Memo1.Lines.Add('--- Итог: ---');
For I := Low(P) To High(P) Do
If P[i] > 0 Then Memo1.Lines.Add(ListBox1.Items[i] + ' --- '+ FloatToStr(P[i]) + ' %');
end;Ну, процедуру ExtractParamNameFromLine думаю сам напишешь. Декларация: Код:
procedure ExtractParamNameFromLine(S : String; var AName : String; var AVal : Double); Последний раз редактировалось lmikle, 27.07.2018 в 01:45. |
| Этот пользователь сказал Спасибо lmikle за это полезное сообщение: | ||
TEKTON (26.07.2018)
| ||
|
#3
|
||||
|
||||
|
lmikle, спасибо.
Цитата:
![]() Чёт я буксую с этой procedure ExtractParamNameFromLine ![]() В первом цикле получаем длинну ListBox Во втором пробегаем по Memo ExtractParamNameFromLine - Парсит название параметра и % Если параметр (pName) не равен нулю, тогда записываем в pIdx номер строки ListBox Далее в масив P заносим номер строки и % Потом в конце это дело записываем в конец Мемо Цитата:
Цитата:
Цитата:
Что передавать этой проуедуре ExtractParamNameFromLine (вроде у неё всё есть) Или что в теле её обрабатывать не догоняю. ![]() Последний раз редактировалось TEKTON, 27.07.2018 в 00:53. |
|
#4
|
|||
|
|||
|
Да ЯТЬ!
Ну просто же. Код:
procedure ExtractParamNameFromLine(S : String; var AName : String; var AVal : Double);
var
sVal : String;
begin
AName := '';
AVal := 0;
If Pos('---',S) > 0 Then
Begin
Try
AName := Trim(Copy(S,1,Pos('---',S)-1));
sVal := Trim(Copy(S,Pos('---',S)+3,Pos('%',S)-Pos('---',S)-3));
AVal := StrToFloat(sVal);
Except
// Нехорошо прятать эксепшены, но лень вспоминать как tryStrToFloat работает
End
End;
end;Как-то так. Если ничего не напутал, то должно работать. ЗЫ. Я там основной исходник тоже поправил чуть-чуть. Последний раз редактировалось lmikle, 27.07.2018 в 01:46. |
| Этот пользователь сказал Спасибо lmikle за это полезное сообщение: | ||
TEKTON (27.07.2018)
| ||
|
#5
|
|||
|
|||
|
Цитата:
![]() Проверил, всё работает чётенько вроде! ![]() Надо наверно в одном посте соединить два кусочка кода. Пригодится ещё кому нить ![]() Код:
{-------------------------- ФУНКЦИЯ --------------------------------}
procedure ExtractParamNameFromLine(S : String; var AName : String; var AVal : Double); // Закодил lmikle http://www.delphisources.ru
var
sVal : String;
begin
AName := '';
AVal := 0;
If Pos('---',S) > 0 Then
Begin
Try
AName := Trim(Copy(S,1,Pos('---',S)-1));
sVal := Trim(Copy(S,Pos('---',S)+3,Pos('%',S)-Pos('---',S)-3));
AVal := StrToFloat(sVal);
Except
// Нехорошо прятать эксепшены, но лень вспоминать как tryStrToFloat работает
End
End;
end;
{------------------------- ЮЗАЕМ -----------------------------}
procedure TForm1.Button1Click(Sender: TObject);
var
P : Array Of Double;
I, pIdx : Integer;
pName : String;
pVal : Double;
begin
SetLength(P,ListBox1.Items.Count);
For I := Low(P) To High(P) Do P[i] := 0; // just in case
For I := 0 To Memo1.Lines.Count-1 Do
Begin
ExtractParamNameFromLine(Memo1.Lines[i],pName,pVal);
If pName <> '' Then
Begin
pIdx := ListBox1.Items.IndexOf(pName);
If pIdx > -1 Then P[pIdx] := P[pIdx] + pVal;
End;
End;
// Print to memo
Memo1.Lines.Add('');
Memo1.Lines.Add('--- Итоговый подсчёт: ---');
Memo1.Lines.Add('');
For I := Low(P) To High(P) Do
If P[i] > 0 Then Memo1.Lines.Add(ListBox1.Items[i] + ' --- '+ FloatToStr(P[i]) + ' %');
end;
Последний раз редактировалось TEKTON, 27.07.2018 в 04:55. |
|
#6
|
|||
|
|||
|
Цитата:
Как раз пригодилось!!!! Спс) |