Navigacija
Lista poslednjih: 16, 32, 64, 128 poruka.

Thred u delphi-u?

[es] :: Pascal / Delphi / Kylix :: Thred u delphi-u?

[ Pregleda: 2033 | Odgovora: 7 ] > FB > Twit

Postavi temu Odgovori

Autor

Pretraga teme: Traži
Markiranje Štampanje RSS

franjo_tahi
Franjo Tahi
Zagreb

Član broj: 34712
Poruke: 399
*.adsl.net.t-com.hr.



+1 Profil

icon Thred u delphi-u?11.02.2011. u 12:45 - pre 160 meseci
Kreiram zaseban thread.
U njemu imam proc Execute u kojoj, nakon što obavim što treba pozovem Terminte.

Kako u programu iz kog sam kreirao thread znam da je thread završio svoje?

Thread mi koristi za sinhronizacije baza, program ga pokreče kada dobije post_event iz baze. Ne znam kada će biti sljedeći i da li će sljedeći doći prije nego je prehdpni thread završio posao. Ja sam dodao property OK koji postavljam na false kada thread završi posao pa ga provjeravam iz programa. Da li može bolje ili jednostavnije? Dolje je kod deklaracije thread-a.

u programu kreiram var myAdressToWeb
Code:

myAdressToWeb = tAdressToWeb.Create(ID);


u procedure tAdressToWeb.Create sam dodao:
Code:

FreeOnTerminate := true;


u proceduri tAdressToWeb.Execute posljenji je radak:
Code:

Terminate;


Provjera iz programa na način:
Code:

if Assigned(AdressToWeb) then ...

ne vrača ispravnu vrijednost, tj. vrati uvijek true, bez obzira da li je thread još aktivan ili je završio svoje.

Code:

   tAdressToWeb = class(TThread)
   private
       fOk: boolean;
       fIO: integer;
       fDataBase: TIBDatabase;
       qLocal: tMyQry;
       qWeb: TADOCommand;
       fMySQL: tMySQL;
       fAdoCon: TADOConnection;
       function IsPuttyRun: boolean;
       function StartPutty: boolean;
       function GetInsertSQL(Value: tMyQry): string;
       function Dat2MySQL(Value: string): string;
   protected
         procedure Execute; override;
   public
         constructor Create(ID: integer);
         destructor Destroy; override;
         property OK: boolean read fOk write fOk;
   end;


Još jedno pitanje: ako trebam startati isti thread prije nego je predhodni završio svoj posao. Kako? U programu koristim var myAdressToWeb za kriranje objekta, predpostavljam da nju ne mogu koristiti ponovo prije nego sam za predhodni napravio free. Pokušao sam preko iste varijeble, tj. kreirati pnovo thread a da predhodni nije završio - oba su ispravno obavila svoj posao. Kako to i smije li to tako?

Da li upoće treba raditi free ako je postavljen FreeOnTerminate := true; i pzvan u threadu: Terminate ?

[Ovu poruku je menjao franjo_tahi dana 11.02.2011. u 13:56 GMT+1]
 
Odgovor na temu

savkic
Igor Savkić

Moderator
Član broj: 92186
Poruke: 2739



+92 Profil

icon Re: Thred u delphi-u?11.02.2011. u 18:04 - pre 160 meseci
> U njemu imam proc Execute u kojoj, nakon što obavim što treba pozovem Terminte.

Nepotrebno, kada se završi Execute gasi se i thread.

> Kako u programu iz kog sam kreirao thread znam da je thread završio svoje?

Možeš pozvati Thread.WaitFor (tako blokiraš program) ili napraviti neki event koji će thread signalizirati kada završi posao (i u programu povremeno proveravati taj event).

> Thread mi koristi za sinhronizacije baza, program ga pokreče kada dobije post_event iz baze. Ne znam kada će biti sljedeći i da li će sljedeći doći prije nego je prehdpni thread
> završio posao. Ja sam dodao property OK koji postavljam na false kada thread završi posao pa ga provjeravam iz programa. Da li može bolje ili jednostavnije?

Ne razumem šta zapravo pitaš.

> Još jedno pitanje: ako trebam startati isti thread prije nego je predhodni završio svoj posao. Kako?

Prosto ga napraviš, samo vodi računa da oba threada ne koriste isti zajednički resurs (vezu ka bazi, dodatne klase i sl.)

> U programu koristim var myAdressToWeb za kriranje objekta, predpostavljam da nju ne mogu koristiti ponovo prije nego sam za predhodni napravio free.

Možeš ako pošto jednom napraviš thread, njega više ne koristiš u glavnom delu. Ako je potrebno da tokom izvršavanja ili na kraju pristupiš threadu onda moraš imati više promenljivih.

> Pokušao sam preko iste varijeble, tj. kreirati pnovo thread a da predhodni nije završio - oba su ispravno obavila svoj posao. Kako to i smije li to tako?

Promenljiva koja ukazuje na neki objekat (kod tebe thread) je samo pointer i kao takav može mu se slobodno menjati sadržaj tj. objekat na koji upućuje.

> Da li upoće treba raditi free ako je postavljen FreeOnTerminate := true; i pzvan u threadu: Terminate ?

Nije potrebno.
 
Odgovor na temu

franjo_tahi
Franjo Tahi
Zagreb

Član broj: 34712
Poruke: 399
*.adsl.net.t-com.hr.



+1 Profil

icon Re: Thred u delphi-u?21.02.2011. u 08:09 - pre 160 meseci
savkic, hvala na pomoći
nisam bio na net-u tjedan dana, godišnji :) (koliko vas je zavodno???)

>> Thread mi koristi za sinhronizacije baza, program ga pokreče kada dobije post_event iz baze. Ne znam kada će biti sljedeći i da li će sljedeći doći prije nego je prehdpni thread
>> završio posao. Ja sam dodao property OK koji postavljam na false kada thread završi posao pa ga provjeravam iz programa. Da li može bolje ili jednostavnije?

> Ne razumem šta zapravo pitaš.

Pitanje je vezano uz pitanje o pokretanju više thread-ova preko iste varijable, shvatio sam. Budući da mogu kreirati thread korištenjem jedne varijable, bez obzira je li predhodni završio posao ili ne, onda mi nije niti bitno da znam njegov status jer ne vraćam ništa iz thread-a u osovni program.

Program koji pišem, a zamislio sam da bi išao preko thread-ova radi sljedeće: sinhronizacija baze na web-u. Podaci iz lokalne baze (nekoliko tablica) koji se lokalno uređuju, upisuju se u skoro istu bazu na web-u.
U thread-u koprisim dinamičko kreiranje kontrola za spajanje na bazu, a parametre čitam iz ini file-a.
 
Odgovor na temu

Rapaic Rajko
Bgd

Član broj: 4105
Poruke: 810
*.dynamic.sbb.rs.



+62 Profil

icon Re: Thred u delphi-u?21.02.2011. u 22:10 - pre 160 meseci
Evo i ja malo da dosolim ;) :

1) Terminate na kraju metode Execute je nepotreban. Cim thread izadje iz Execute metode, isti je 'auto-terminiran', i uz FreeOnTermionate := true, sam se i ubija.

2) Sinhronizacija nad bazom... hm. Da li je baza sama po sebi threadsafe? Ako NE, onda moras da uradis serijalizaciju ('u red') thread-ova koji po njoj drljaju, jos bolje na nivou tabela. Najjednostavnije je da napravis 'usko grlo' uz jedan lock objekat, to bi bio par procedura sa recimo critical section-om. Prva procedura radi lock, druga unlock. Prvu proceduru pozivas na pocetku metode Execute, drugu na kraju iste. Tako thread-ove redjas ko 'ptice na zici', i osiguravas da uvek samo jedan stvarno radi.
Slozenije/bolje resenje je da napravis klase za pristup tabelama, za svaku tabelu po jednu klasu. U svakoj klasi napravis lock i unlock metode (znaci koliko tabela toliko i lock objekata), koje pozivas opet iz Execute metode. Na taj nacin uvek samo jedan thread radi nad jednom odredjenom tabelom; sto znaci, moguce je da rade vise thread-ova istovremeno, ali ne nad istom tabelom.

Uh, ako je ovo prekomplikovano (i ako nisam promasio temu :) ), reci, i pojasnice se...

Pozzz

Rajko
 
Odgovor na temu

franjo_tahi
Franjo Tahi
Zagreb

Član broj: 34712
Poruke: 399
*.adsl.net.t-com.hr.



+1 Profil

icon Re: Thred u delphi-u?22.02.2011. u 11:05 - pre 160 meseci
Rajko, mislim da shvaćam o čemu pričaš.

Kod mene su: localno - firebird, web - MySQL

Koliko sam shvatio, serializaciju je potrebno napraviti da bi se spriječilo da dva thread-a rade na istom slogu. Za moj konkretan slučaj je to (skoro) nemoguće jer se izmjene ili upisi rade s orgonalnih dokumenata i dvije osobe ih ne mogu obrađivati. Mogu raditi na istoj tabeli (npr adresar) ali ne na istom slogu.

Malo sam izmjenio koncept, sada mi svaka tablica koju je potrebno sinhronizirati ne generira postevent već tablica u trigeru afterpost (insert) upisuje u tablicu "izmjene" atribute: ime_tablica, key_value, web_update tako da znam koji slog moram sinhronizirati sa web-om. Ta nova tablica generira postevent, a u main-u, preko ime_tablice znam koji thread moram pokrenuti i koji slog treba sinhronizirati.
Thread nakon što obavi svoj posao, u "izmjene.web_update" upisuje datum i vrijeme sinhronizacije. Tako znam koji podatak sam kada sinhronizirao, a sinhroniziram samo one gdje je: WEB_UPDATE IS NULL
Mogao sam i preko timer-a, a bez post_evet-a iz baze, čitati podatke za update, ali mi je ovako elegantnije, a i ne starta se provjera ako nema podataka za update, ne izvršava se SQL koji ih čita...

Možda sam mogao upistivati datum izmjene u lokalnoj bazi u svakoj tablici zasebno, ali ovako mi ostaje povjest izmjena.

Svaki savjet je dobrodošao jer sam novi u području thread-ova.
 
Odgovor na temu

franjo_tahi
Franjo Tahi
Zagreb

Član broj: 34712
Poruke: 399
*.adsl.net.t-com.hr.



+1 Profil

icon Re: Thred u delphi-u?28.02.2011. u 08:06 - pre 159 meseci
Još jedna nedoumica:

U svakom thread-u koji kreiram, kreiram zasebni set kontrola za pristup MySQL bazi: TADOConnection i TADOCommand;

Što je bolje, kreirati jedan TADOConnection u main formi, otvori ga, pa ga prosljeđivati u thread ili u svakom threadu kreirati zasebnu konekciju?
 
Odgovor na temu

exdatis
Morar Zivica
Programer

Član broj: 92230
Poruke: 107
*.static.madnet.rs.



+1 Profil

icon Re: Thred u delphi-u?28.02.2011. u 08:57 - pre 159 meseci
Svako ponovno uspostavljanje konekcije je "skup" proces, svakako.
Logicnije zvuci da u nekom(recimo DataModule) objektu kreiras konekciju,
i nju koristis tamo gde ti je potrebna, pod uslovom da zaista i zelis da
konekciju zadrzis otvorenom(mozda nije tako ako se radi preko interneta sa velikim skupom podataka).
Sve to moze i drugacije ako koristis troslojnu arhitekturu(baza-server(servis)-klijent), a svakako
je dobro imati samo jedan konekcioni objekat iako mu menjas svojstva ili zatvaras i otvaras konekciju vise puta,
bitno je da on moze da "deli informacije" sa ostalim objektima u aplikaciji, bilo na koji nacin da dodjes do tog
objekta(referenca, pokazivac) pa tako i svaka nit moze da koristi ove informacije.
Ako si vec uspostavio kontrolu nad nitima(sta-ko radi u bazi(prethodni komentari)) onda je ovo logicnije.
 
Odgovor na temu

savkic
Igor Savkić

Moderator
Član broj: 92186
Poruke: 2739



+92 Profil

icon Re: Thred u delphi-u?28.02.2011. u 09:27 - pre 159 meseci
> u svakom thread-u koji kreiram, kreiram zasebni set kontrola za pristup MySQL bazi: TADOConnection i TADOCommand;
> Što je bolje, kreirati jedan TADOConnection u main formi, otvori ga, pa ga prosljeđivati u thread ili u svakom threadu kreirati zasebnu konekciju?

Mislim da AdoConnection nije thread safe tako da moraš imati posebnu instancu za svaki thread.
 
Odgovor na temu

[es] :: Pascal / Delphi / Kylix :: Thred u delphi-u?

[ Pregleda: 2033 | Odgovora: 7 ] > FB > Twit

Postavi temu Odgovori

Navigacija
Lista poslednjih: 16, 32, 64, 128 poruka.