Autor Téma: Návrh typu pro regex - problém s vnořením do sebe sama  (Přečteno 1330 krát)

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #30 kdy: 15-06-2019, 18:39:39 »
I found the clue

Kód: Delphi [Vybrat]
  1. pSec.hasSections := true;
  2. setlength(psec.secs, psec.len+1);
  3. psec.secs[psec.len] := New(PTRegex_sec);
  4. psec.secs[psec.len].parent := psec;
  5. Inc(psec.len);
  6.  
« Poslední změna: 15-06-2019, 18:42:32 od vangog »

Offline Delfin

  • Padawan
  • ******
  • Příspěvků: 1823
  • Karma: 70
  • SW konzultant
    • Verze Delphi: 2009, Tokyo, Rio
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #31 kdy: 15-06-2019, 18:49:29 »
Good
Rated 1 time
Nerozumím vám, musíte na mě polopaticky.

Chtel jsem rict ze ^PointerVariable (kde PointerVariable by byla promenna) by nedavalo smysl. Caret operator ^ pred identifikatorem se totiz pouziva k notaci ukazatele na datovy typ v deklaracich, tj. napr.:

Kód: Delphi [Vybrat]
  1. type
  2.   PInteger = ^Integer; // notace datoveho typu ukazatele na Integer

V nasledujici ukazce by inspekce hodnoty promenne P zpusobem ^P nedavala smysl:

Kód: Delphi [Vybrat]
  1. var
  2.   P: PInteger;
  3. begin
  4.   P^ := 123; // inspekce ^P by nedavala smysl; k inspekci hodnoty je treba pouzit dereferenci zapisem P^
  5. end;

Takže když používám setlength rekurzivně, musím to potom zase rekurzivně uvolnit z paměti, nebo se to uvolňuje samo?

Pro dynamicka pole Delphi kompilator generuje kod pro uvolneni. To ovsem nemusi platit pro cleny takoveho pole.

Ptal jsem se předtím na stackoverflow na to jak mám nastavovat ten typ sekce a bylo mi řečeno, že první úroveň (wrapper) mmám nastavit tím setlength. A ty vnořené, že jim musím předělit paměť pomocí New.

Neznam souvislosti, ale obecne pravidlo kterym se ridit muze znit, co si rucne alokujes nasledne uvolni (alokaci je v tomto pripade funkce New). Co se tyce alokace pole, to se bude provadet vzdy pomoci SetLength, nehlede na uroven vnoreni stromu; tzn.:

Kód: Delphi [Vybrat]
  1. type
  2.   PMyRecord = ^TMyRecord;
  3.   TMyRecord = record
  4.     InnerArray: array of PMyRecord; // vnitrni pole ukazatelu na tuto strukturu
  5.   end;
  6.  
  7. var
  8.   MyRecord: TMyRecord;
  9. begin
  10.   SetLength(MyRecord.InnerArray, 1); // alokace vnitrniho pole na 1 prvek; prvek alokovan neni jelikoz nejde o hodnotovy typ ale o ukazatel
  11.   MyRecord.InnerArray[0] := New(PMyRecord); // alokace struktury TMyRecord s naslednym prirazenim 1. prvku pole
  12.   try
  13.     SetLength(MyRecord.InnerArray[0]^.InnerArray, 1); // stejnym zpusobem se alokuje pole i prvku vnitrniho pole vychoziho zaznamu
  14.     MyRecord.InnerArray[0]^.InnerArray[0] := New(PMyRecord); // stejne jako predtim je treba alokovat prvek pole
  15.     try
  16.       ...
  17.     finally
  18.       Dispose(MyRecord.InnerArray[0]^.InnerArray[0]); // uvolneni manualne alokovane struktury
  19.     end;
  20.   finally
  21.     Dispose(MyRecord.InnerArray[0]); // uvolneni manualne alokovane struktury
  22.   end;
  23. end;

Mozna si jen pletes alokaci pole s alokaci jeho clenu.
I'm a soldier, so don't panic! I know the underground! I like the WTFPL license! No more Google, go duck, go!

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #32 kdy: 15-06-2019, 19:58:19 »
Já jsem dlouze přemýšlel v čem dělám chybu. Furt jsem myslel na to nil (element pole, jak se tam dostal). Pak mi to najednou došlo. Že to přižazování se tam děje ve dvou úrovních. První úroveň je nastavení délky pole pointerů... Tím se tam dostane to nil. A druhá úroveň je pak to, že ten pointer musí někam směřovat, tedy tomu objektu přidělím paměť... Takže jsem z toho konečně moudřejší.

Navíc jsem řešil jak si pohlídat dealokování všech těch elementů, abych to nedělal rekurzivně. Tak jsem vymyslel toto

Kód: Delphi [Vybrat]
  1. destructor TTrackerRegex.Destroy();
  2. var i: integer;
  3. begin
  4. { Despose all objects from the last one
  5.   to the first one }
  6.   for i := info.AllSecPointers_currentIndex downto 0 do
  7.      Dispose(AllSecPointers[i]);
  8.    inherited;
  9. end;
  10.  

info.AllSecPointers_currentIndex se nastaví vždycky když allokuju paměť pro vnořenou sekci, čili nastavuju ukazatel pro element pole pointerů. A každý ukazatel si zazálohuju do pole, kde všechno sbírám. Toto pole je jednorozměrné, takže se vše dá snadno dealokovat.

Procedura pro alokování paměti vnořených objektů:

Kód: Delphi [Vybrat]
  1. procedure TTrackerRegex.incSection(newLevel: boolean; pSec: pTRegex_sec = nil);
  2. begin
  3.   if (pSec = nil ) then
  4.     begin
  5.       Sections := New(pTRegex_sec);
  6.       // Backup pointer
  7.       AllSecPointers[0] := Pointer(Sections);
  8.       info.AllSecPointers_currentIndex := 1;
  9.       // The root section parent is self
  10.       Sections.parent := Sections;
  11.       Sections.len := 0;
  12.       Sections.hasSections := false;
  13.       Sections.hasUnits    := false;
  14.       exit;
  15.     end;
  16.   if (not newLevel) then
  17.     begin // EXPAND SECTION
  18.       setlength(psec.secs, psec.len+1);
  19.       psec.secs[psec.len] := New(PTRegex_sec);
  20.       // Backup pointer
  21.       AllSecPointers[info.AllSecPointers_currentIndex] := Pointer(Sections);
  22.       Inc(info.AllSecPointers_currentIndex);
  23.       if (info.AllSecPointers_currentIndex>length(AllSecPointers)) then
  24.         setLength(AllSecPointers,length(AllSecPointers)+10);
  25.       psec.secs[psec.len].parent := psec.secs[psec.len];
  26.       Inc(psec.len);
  27.     end
  28.   else
  29.     begin // CREATE NEW LEVEL INTO CURRENT SECTION
  30.       pSec.hasSections := true;
  31.       setlength(psec.secs, psec.len+1);
  32.       psec.secs[psec.len] := New(PTRegex_sec);
  33.       // Backup pointer
  34.       AllSecPointers[info.AllSecPointers_currentIndex] := Pointer(psec.secs[psec.len]);
  35.       Inc(info.AllSecPointers_currentIndex);
  36.       if (info.AllSecPointers_currentIndex>length(AllSecPointers)) then
  37.         setLength(AllSecPointers,length(AllSecPointers)+10);
  38.       psec.secs[psec.len].parent := psec;
  39.       Inc(psec.len);
  40.     end;
  41. end;
  42.  
  43.  

Zítra bych tam mohl přidat try block. Já to normálně nepoužívám, ale tu by to nejspíš chtělo.

Dotaz:
Když to ladím stylem, že dám zarážku, alokuju paměť, zastavím na zarážce a pak restartuju debugger, tak dojde k "memory leak"? Protože debugger mi opakovaně padá.

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #33 kdy: 15-06-2019, 20:05:37 »
Citace
Když to ladím stylem, že dám zarážku, alokuju paměť, zastavím na zarážce a pak restartuju debugger, tak dojde k "memory leak"? Protože debugger mi opakovaně padá.
Ty nepoužívaš napr. FMM4? Ja bez toho neurobím pri ladení ani krok!
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #34 kdy: 15-06-2019, 21:20:07 »
FMM4? Kde se to dá sehnat a jak se to používá? Tedy pokud je to pro Delphi7?

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #35 kdy: 15-06-2019, 21:27:24 »
Poor
Rated 1 time
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #36 kdy: 15-06-2019, 21:31:50 »
Aby som nebol zlý, tak doplňujem:
Kód: Delphi [Vybrat]
  1. program PoBeS;
  2. {$R *.dres}
  3. uses
  4.   {$IFDEF DEBUG}
  5.   FastMM4 in 'C:\Users\Public\Documents\Embarcadero\Studio\FastMM4\FastMM4.pas',
  6.   FastMM4Messages in 'C:\Users\Public\Documents\Embarcadero\Studio\FastMM4\FastMM4Messages.pas',
  7.   {$ENDIF }
  8. ...
V každom prípade si prejdi konfiguračný súbor a zapni full debug mode. Budeš si musieť skopírovať knižnice k exe. Tu v diskusiách sa to už preberalo niekoľkokrát :(
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #37 kdy: 15-06-2019, 23:06:00 »
Ale já nemám Embarcadero Delphi

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #38 kdy: 16-06-2019, 09:19:30 »
Ale já nemám Embarcadero Delphi
Na tom vôbec nezáleží. Ja som Ti len dal príklad ako sa to má použiť. Musí to byť uvedené ako prvé. A je úplne jedno aké cesty si tam dáš!
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #39 kdy: 16-06-2019, 15:06:08 »
Dík za odkaz, ale nevím kdy budu mít čas to zkoumat.

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #40 kdy: 16-06-2019, 16:30:25 »
Dík za odkaz, ale nevím kdy budu mít čas to zkoumat.
Ak máš na mysli FMM4, tak tam nemáš čo skúmať.
  • Nakopíruješ si potrebné súbory na správne miesta
  • Do *.dpr pridáš 2/4 riadky
  • Upravíš konfiguračný súbor - do 10 min. Je dobre komentovaný
  • Modlíš sa, aby Ti nič nevypísal ;) 
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #41 kdy: 17-06-2019, 09:32:12 »
Staženo mám. Musím něco kompilovat?
Jsou tam dvě složky jedna "FullDebugMode DLL" a druhá "Replacement BorlndMM DLL\Delphi" ta obsahuje "FastMMDebugSupport.pas" a pak je tam precompiled\for Delphi IDE\Performance

Tak nevím co mám vybrat. Mám tu složku někam zkopírovat nebo nic nekopírovat jen vybrat cestu?

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #42 kdy: 17-06-2019, 09:43:12 »
Citace
Musím něco kompilovat?
Nie.
Pre D7 si to už nepamätám.
Tam kde sa vytvára *.exe (Debug adresár) mám
  • FastMM_FullDebugMode.dll
  • FastMM_FullDebugMode64.dll
Ostatné mám vo vlastnom adresári, ktorý používam pre všetky aplikácie. Viď moje dpr. Tam mám všetko
  • FastMM_FullDebugMode.dll
  • FastMM_FullDebugMode64.dll
  • FastMM4.dcu
  • FastMM4.pas
  • FastMM4Messages.dcu
  • FastMM4Messages.pas
  • FastMM4Options.inc
Urob si to podobne. Ak bude niečo zle, tak dostaneš oznam o chýbajúcej knižnici. To si už vyriešiš.
Určite si si stiahol aj súbor ako to inštalovať. Čo sa tak doň pozrieť?
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.

Offline vangog

  • Hrdina
  • ****
  • Příspěvků: 370
  • Karma: 0
    • Verze Delphi: 7
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #43 kdy: 17-06-2019, 11:12:46 »
Nápovědu k instalaci jsem nenašel. Nicméně si nemohu vzpomenout kde v Delphi 7 najdu nastavení projektu -> Linker abych tam přidal tu zkompilovanou knihovnu. Mám tam Project->Options->Directories ... tam nic nastaveno není. A Pod kartou Linker taky není seznam ovladačů. Mám tam nainstalované nějaké balíčky, ale to je něco jiného...

Edit:
Ta direktiva {$R *.dres} znamená co? To tam taky musím dát?
« Poslední změna: 17-06-2019, 11:20:32 od vangog »

Offline Stanislav Hruška

  • Padawan
  • ******
  • Příspěvků: 4338
  • Karma: 38
    • Verze Delphi: XE7 professional
Re:Návrh typu pro regex - problém s vnořením do sebe sama
« Odpověď #44 kdy: 17-06-2019, 11:29:59 »
Citace
Nápovědu k instalaci jsem nenašel.
To som sa pomýlil. Mal som na mysli návod. Zvyčajne ReadMe.
Citace
Ta direktiva {$R *.dres} znamená co? To tam taky musím dát?
Nie, to je odkaz na resource.
Mám zozbierané návody, ale spakované majú 1,3 MB. Tu sa nedajú priložiť. Pošli mi mail, aby som Ti to poslal.
Delphi XE7, FireBird
Expert na kladenie nejasne formulovaných otázok.