Search  
Monday, December 09, 2019 ..:: Forum ::.. Register  Login
 Forum Minimize
Pentru a putea posta mesaje trebuie să vă înregistraţi.
Notă: Mesajele cu conţinut jignitor sau ilegal (inclusiv cereri de soft piratat) nu sunt acceptate şi vor fi şterse imediat .

Pentru a primi raspunsuri rapide si corecte, scrieti in mesaj ce intentionati sa faceti, ce mesaj de eroare primiti, in ce context si in urma caror actiuni. De asemenea, mentionati versiunea de FoxPro in care lucrati!
Dacă nu specificați versiunea, se consideră VFP 9.0 SP2.

SearchForum Home
  Visual FoxPro  Baze de date, tabele, view-uri si indecsi  Nomencaltor con...
 Nomencaltor conturi
 
 11/3/2012 2:02:16 PM
User is offlineEugen Gliga
2092 posts
1st




Nomencaltor conturi
 (N/A)
Teoretic un nomenclator de conturi este format din clase,grupe,conturi de gradul 1 si conturi de gradul 2. Functionale sunt doar conturile cu gradul cel mai mare, celelalte fiind doar un total al conturilor de grad superioar. Ca si observatie, multe programe nu respecta aceasta regula, de exemplu se lucreaza cu contul 401 si apoi se mai adauga un 4011 care functioneaza separat fara sa fie inclus in 401. Revenind la subiect, se da o tabela cu campul Simbol de tip caracter. Ceva gen:
5
53
531
5311
5312
532
54
541

In acest exemplu conturile functionale sunt 5311,5312,532 si 541
Cu greu am reusit sa fac un select doar pentru conturile functionale.
Ceva gen:
Select Simbol From Nomcont Into Cursor xxx Where Simbol Not In (Select Distinct Padr(Left(Simbol,Len(Alltrim(Simbol))-1),9) From Nomcont ) Order By Simbol
Nici nu sunt sigur daca functioneaza in toate cazurile particulare

N-am reusit sa fac un Select care sa contina doar conturile de total.
In acest caz doar 5. Daca sterg 5 ar trebui sa apara doar 53 si 54.
Daca sterg 5 si 53 ar trebui sa ramana doar 531 532 si 54.



 11/3/2012 4:19:45 PM
User is offlineadimorarasu
89 posts
morarasu-adrian.num.ro




Re: Nomencaltor conturi
 (N/A)
De ce nu bagi un cimp numit activ, care poate fi si logical sau c(1)?
 11/3/2012 5:44:58 PM
User is offlineGrigore Dolghin
3996 posts
www.class-software.ro
1st






Re: Nomencaltor conturi
 (N/A)
Eugen, asta e o problema tipica de ierarhie.

Pentru tabelele ierarhice exista doua moduri de stocare: "nested set model" si "adjacency list". Ambele au avantaje si dezavantaje, asa ca alegerea unuia depinde de modul in care sunt folosite datele. Pentru cazul tau as folosi adjacency list.

Nu esti primul are are problema asta si nici ultimul. Din fericire toate teoriile astea au fost fundamentate acum multa vreme (adjacency list are vreo 40 de ani, cred) si trebuie doar folosite. Dar ca sa le folosesti, trebuie sa le cunosti in prealabil :( De-aia e buna o carte din cand in cand.

Adjacency list:

ID, PARENT_ID, CONT
1, NULL, 5
2, 1, 53
3, 2, 531
4, 3, 5311
5, 3, 5312
6, 2, 532
7, 1, 54
8, 7, 541

Daca vrei sa selectezi numai conturile de total, SELECT * From conturi where PARENT_ID IS NULL.

Daca stergi contul 5 va trebui sa inlocuiesti in toate conturile subordonate _direct_ lui 5 PARENT_ID cu NULL, ca sa stii ca ala e acum contul de total. Si tot asa. INSERT, UPDATE si DELETE se fac avand grija sa modifici si contul parinte, daca este cazul.

Grigore Dolghin
Visual FoxPro MVP 2006 - 2010
Class Software
My blog
 11/3/2012 6:03:07 PM
User is offlinealemao
344 posts
3rd


Re: Nomencaltor conturi
 (N/A)
Hhhhmmmm, ceea ce ai 531, 532 541 sunt conturi sintetice de gradul unu, iar 5311, 5312 sunt conturi sintetice de gradul doi.
Ce te faci atunci cand ai si conturi analitice - ca doar evidenta tertilor se tine pe analitice.
Spre exemplu contul sintetic de gradul I - 411 are un sintetic de gradul II - 4111 si la care se poate adauga ceva de genul
4111.0001 - clientul x
4111.0002 - clientul y
Si crede-ma, sunt patroni, directori etc. care vor sa-i vada pe acesti clienti in balanta analitica semnata de cei de la contabilitate
ca sa fie el sigur care nu nimic bagat sub preş.

Subscriu si eu la adaugarea unei coloane in care sa se stocheze care sa faca referire la faptul ca un cont ARE / NU ARE analitice - chestie obligatorie incepand cu conturile sintetice de gradul I
 11/3/2012 6:34:38 PM
User is offlineCostel
328 posts
www.adrisoft.ro
3rd




Re: Nomencaltor conturi
 (N/A)
In FireBird a mers urmatoarea comanda:
SELECT Cat.cont,Cat.denumire FROM catalog Cat where not exists ( select Kat.cont from catalog Kat where Kat.cont starting with trim(Cat.cont) and Kat.cont<>Cat.cont) and Cat.cont starting with '5' order by Cat.cont

in VFP 8.0 nu-mi iese
eu folosesc un cimp aditional


Nu munci atit de mult incit sa nu-ti mai ramina timp ca sa cistigi bani. (proverb evreiesc)
 11/3/2012 7:49:33 PM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Se pare ca asta este solutia corecta. Dezavantajul este ca accidental, parent_id-ul poate fi eronat.
Eu pana acum am folosit o functie care imi calcula gradul contului fara sa-l stocheze. La o parcurgere secventiala a tabelei era ok, dar la sql  solutia a devenit incomoda.
Am vazut ca este pe net suficienta documentatie despre "adjacency list", asa ca trebuie doar sa cautam si sa citim, nu mai e necesar sa reinventam roata.
Mai am o intrebare. Stiu ca exista un motiv pentru care ai folosit NULL in loc de 0, pentru PARENT_ID. Cred ca sa mai discutat problema asta pe lista, dar imi scapa acum.


 11/4/2012 10:38:51 AM
User is offlineGrigore Dolghin
3996 posts
www.class-software.ro
1st






Re: Nomencaltor conturi
 (N/A)
Merge si zero :) eu am folosit null in virtutea obisnuintei.

Grigore Dolghin
Visual FoxPro MVP 2006 - 2010
Class Software
My blog
 11/4/2012 10:44:35 AM
User is offlineGrigore Dolghin
3996 posts
www.class-software.ro
1st






Re: Nomencaltor conturi
 (N/A) Modified By Grigore Dolghin  on 11/4/2012 10:51:17 AM)
Ar mai fi o chestie de zis aici: la modelul adjacency list operatiunile la nivel de inregistrare sunt simple, dar select-ul e complicat. La nested model, selectul este simplu, dar managementul inregistrarilor e complicat.

La adjacency list daca ai nevoie sa descarci o inregistrare si toate inregistrarile subordonate ei, pana la al n-spelea nivel, trebuie sa scrii o procedura care se apeleaza recursiv. Un exemplu functional ai aici: http://fox.wikis.com/wc.dll?Wiki~RecursiveData

Joe Celko a scris o carte foarte misto, numita "Trees and Hierarchies in SQL for Smarties" in care discuta pe larg despre subiectul asta. Cartea - ma uit acum la ea, e la mine pe birou. Un articol care provine din ea gasesti aici: http://www.sqlsummit.com/AdjacencyList.htm

Grigore Dolghin
Visual FoxPro MVP 2006 - 2010
Class Software
My blog
 11/4/2012 12:30:35 PM
User is offlineGrigore Dolghin
3996 posts
www.class-software.ro
1st






Re: Nomencaltor conturi
 (N/A)
 alemao wrote
Hhhhmmmm, ceea ce ai 531, 532 541 sunt conturi sintetice de gradul unu, iar 5311, 5312 sunt conturi sintetice de gradul doi.
Ce te faci atunci cand ai si conturi analitice - ca doar evidenta tertilor se tine pe analitice.
Spre exemplu contul sintetic de gradul I - 411 are un sintetic de gradul II - 4111 si la care se poate adauga ceva de genul
4111.0001 - clientul x
4111.0002 - clientul y
Si crede-ma, sunt patroni, directori etc. care vor sa-i vada pe acesti clienti in balanta analitica semnata de cei de la contabilitate
ca sa fie el sigur care nu nimic bagat sub preş.

Subscriu si eu la adaugarea unei coloane in care sa se stocheze care sa faca referire la faptul ca un cont ARE / NU ARE analitice - chestie obligatorie incepand cu conturile sintetice de gradul I


Adaugarea unei coloane pentru ARE/NU ARE analitice nu e necesara ca sa afli daca are sau nu analitice.

SELECT pc.ID, pc.PARENT_ID, pc.CONT, (SELECT COUNT(*) FROM plan_conturi pc2 WHERE pc.ID = pc2.PARENT_ID) As NrAnalitice FROM planconturi pc

Instructiunea de mai sus descarca inregistrarile din tabela planconturi si face un subselect pe aceeasi tabela care returneaza numarul de inregistrari subordonate. Daca e mai mare ca zero, are analitice. Daca nu, nu.

Grigore Dolghin
Visual FoxPro MVP 2006 - 2010
Class Software
My blog
 11/5/2012 1:51:33 AM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Interesant SELECT-ul, dar cred ca e ceva in neregula cu el. Functioneaza, dar rezultatul este eronat. Nu inteleg conditia pc.ID=pc2.PARENT_ID.
Dupa mine SELECTUL ar trebui sa arate asa:

SELECT pc.ID, pc.PARENT_ID, pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc2.PARENT_ID>pc.Parent_ID AND pc2.simbol=Allt(pc.Simbol) ) As NrAnalitice FROM conturi pc

dar nu stiu de ce Allt(pc.Simbol) produce o eroare. Functia Allt este suportata doar de pc2.Simbol

Dar tot raul spre bine. Tot studiind acest select am gasit raspunsul la intrebarea mea initiala adica un select doar pentru conturile de total, de grad minim fara introducerea de campuri suplimentare:

CREATE table conturi (Simbol c(9))
*INSERT INTO conturi (simbol) VALUES ("5")
*INSERT INTO conturi (simbol) VALUES ("53")
INSERT INTO conturi (simbol) VALUES ("531")
INSERT INTO conturi (simbol) VALUES ("5311")
INSERT INTO conturi (simbol) VALUES ("5312")
INSERT INTO conturi (simbol) VALUES ("532")
*INSERT INTO conturi (simbol) VALUES ("54")
INSERT INTO conturi (simbol) VALUES ("541")
INSERT INTO conturi (simbol) VALUES ("542")
SELECT pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc.simbol=ALLTRIM(pc2.Simbol))-1 As NrAnalitice FROM conturi pc HAVING NrAnalitice=0


 11/5/2012 1:57:34 AM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Intamplator, dupa prima ta postare, am dat o cautare pe Google si am nimerit chiar peste articolul asta de care zici. Articolul este foarte interesant, urmeaza sa-l aprofundez.


 11/5/2012 2:39:40 AM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Se poate introduce un astfel de camp dar el trebuie gestionat automat. Adica daca initial  401 este marcat ca nu are conturi de grad superior, in momentul in care am introdus contul 4011 in nomenclator automat 401 trebuie marcat ca are astfel de conturi. In momentul in care sterg toate conturile de grad superior lui 401, acesta trebuie  marcat ca neavand astfel de conturi. Nu pot lasa  gestionarea acestui camp pe seama userului pentru a evita sa fiu in eroare. Pai  campul  Parent_Id din modelul Adjacency List chiar asta face si cred ca o face mai bine.

Asta referitor la sintetice de diverse grade. Referitor la analitice, abordarea mea este alta. Pentru conturile de grad maxim pot bifa diverse analitice, pe partener, pe cod produs pe valuta, etc
Analiticele respective sunt intr-un fisier separat. Era vorba doar despre un plan de conturi. Nu cred ca tine nimeni in planul de conturi analitice gen 4111.0001
De fapt aveam doua probleme. Sa fac un select simplu din planul de conturi atat pentru conturile de grad maxim, adica conturile functionale cat si pentru conturile de grad 0, adica doar conturile de total. Se pare ca Adjacency List rezolva ambele probleme.


 11/5/2012 10:12:40 AM
User is offlineGrigore Dolghin
3996 posts
www.class-software.ro
1st






Re: Nomencaltor conturi
 (N/A)
Eh, din pacate timpul meu liber este foarte foarte putin si atunci cand il am prefer sa ma urc pe motor si sa ma duc unde vad cu ochii. Dar fiindca vine iarna sper sa ma pot tine de promisiunea cu clasa de meniuri (s-a discutat in alt thread) si sa scriu un articol despre nested set model, care e suprinzator :)

Grigore Dolghin
Visual FoxPro MVP 2006 - 2010
Class Software
My blog
 11/6/2012 4:44:21 PM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Am ramas in urma acestui thread cu o nelamurire referitoare la o comanda SQL. In codul de mai jos primul SELECT este  Ok si da rezultatul scontat, iar al doilea da eroarea SQL: Error correlating fields. Eroarea apare doar daca folosesc in WHERE, ALLTRIM(pc.Simbol). Daca folosesc doar "pc2.Simbol" eroarea nu mai apare, dar atunci rezultatul nu este cel scontat.
M-ar interesa atat explicatia cat si solutia.


CREATE cursor conturi (Simbol c(9))
*INSERT INTO conturi (simbol) VALUES ("5")
*INSERT INTO conturi (simbol) VALUES ("53")
INSERT INTO conturi (simbol) VALUES ("531")
INSERT INTO conturi (simbol) VALUES ("5311")
INSERT INTO conturi (simbol) VALUES ("5312")
INSERT INTO conturi (simbol) VALUES ("532")
*INSERT INTO conturi (simbol) VALUES ("54")
INSERT INTO conturi (simbol) VALUES ("541")
INSERT INTO conturi (simbol) VALUES ("542")
* Select doar conturi de grad minim Ok
SELECT pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc.Simbol=ALLTRIM(pc2.Simbol))-1 As Grad FROM conturi pc HAVING Grad=0
* Select doar conturi fara analitice
SELECT pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc2.Simbol=ALLTRIM(pc.Simbol))-1 As NrAnalitice FROM conturi pc HAVING NrAnalitice=0

 11/6/2012 11:45:10 PM
User is offlineDaniel Buduru
3513 posts
1st




Re: Nomencaltor conturi
 (Romania)
 Eugen Gliga wrote
Interesant SELECT-ul, dar cred ca e ceva in neregula cu el. Functioneaza, dar rezultatul este eronat. Nu inteleg conditia pc.ID=pc2.PARENT_ID.


Asta este structura tabelei pe care functioneaza corect selectul dat de Grig:

CREATE cursor conturi (id i, parent_id i null, cont c(10))
INSERT INTO conturi VALUES (10, null, "5")
INSERT INTO conturi VALUES (99,null,"53")
INSERT INTO conturi VALUES (30,99,"531")
INSERT INTO conturi VALUES (40,30,"5311")
INSERT INTO conturi VALUES (50,30,"5312")
INSERT INTO conturi VALUES (60,99,"532")
INSERT INTO conturi VALUES (70,null,"54")
INSERT INTO conturi VALUES (80,70,"541")
INSERT INTO conturi VALUES (90,70,"542")

SELECT pc.ID, pc.PARENT_ID, pc.CONT, (SELECT COUNT(*) FROM conturi pc2 WHERE pc.ID = pc2.PARENT_ID) As NrAnalitice FROM conturi pc

ID si simbol cont sunt diferite, iar despre ID nu se poate presupune ca este in ordine strict crescatoare.



Daniel Buduru
 11/7/2012 12:25:54 AM
User is offlineDaniel Buduru
3513 posts
1st




Re: Nomencaltor conturi
 (Romania) Modified By Daniel Buduru  on 11/7/2012 12:36:00 AM)
 Eugen Gliga wrote
Am ramas in urma acestui thread cu o nelamurire referitoare la o comanda SQL. In codul de mai jos primul SELECT este  Ok si da rezultatul scontat, iar al doilea da eroarea SQL: Error correlating fields. Eroarea apare doar daca folosesc in WHERE, ALLTRIM(pc.Simbol). Daca folosesc doar "pc2.Simbol" eroarea nu mai apare, dar atunci rezultatul nu este cel scontat.
M-ar interesa atat explicatia cat si solutia.


CREATE cursor conturi (Simbol c(9))
*INSERT INTO conturi (simbol) VALUES ("5")
*INSERT INTO conturi (simbol) VALUES ("53")
INSERT INTO conturi (simbol) VALUES ("531")
INSERT INTO conturi (simbol) VALUES ("5311")
INSERT INTO conturi (simbol) VALUES ("5312")
INSERT INTO conturi (simbol) VALUES ("532")
*INSERT INTO conturi (simbol) VALUES ("54")
INSERT INTO conturi (simbol) VALUES ("541")
INSERT INTO conturi (simbol) VALUES ("542")
* Select doar conturi de grad minim Ok
SELECT pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc.Simbol=ALLTRIM(pc2.Simbol))-1 As Grad FROM conturi pc HAVING Grad=0
* Select doar conturi fara analitice
SELECT pc.Simbol, (SELECT COUNT(*) FROM Conturi pc2 WHERE pc2.Simbol=ALLTRIM(pc.Simbol))-1 As NrAnalitice FROM conturi pc HAVING NrAnalitice=0


Selectul care da NrAnalitice este un subquery corelat (este filtrat dupa un camp din tabela utilizata in query principal). VFP nu suporta alterarea campurilor din tabelele utilizate in query principal pe care se face corelarea, prin functii care sa-i modifice valoarea: trim, left, right, subs, val, etc, si nici operatorul like.
Prima comanda functioneaza pentru ca nu este alterat campul pc.simbol, trimarea este aplicata doar pe pc2.simbol.

O solutie este urmatoarea :

CREATE cursor conturi (Simbol c(9))
INSERT INTO conturi (simbol) VALUES ("5")
INSERT INTO conturi (simbol) VALUES ("53")
INSERT INTO conturi (simbol) VALUES ("531")
INSERT INTO conturi (simbol) VALUES ("5311")
INSERT INTO conturi (simbol) VALUES ("5312")
INSERT INTO conturi (simbol) VALUES ("532")
INSERT INTO conturi (simbol) VALUES ("54")
INSERT INTO conturi (simbol) VALUES ("541")
INSERT INTO conturi (simbol) VALUES ("542")

* Pentru a vedea cursorul returnat de subquery
SELECT pc.simbol, pc2.simbol as simbol_a FROM conturi pc LEFT JOIN conturi pc2 ON pc2.simbol like TRIM(pc.simbol)+'%' AND pc.simbol<>pc2.simbol;
Into cursor crs1
BROW NOWAIT

*Toate conturile
SELECT simbol, sum(IIF(ISNULL(simbol_a),0,1)) as NrAnalitice FROM ;
(SELECT pc.simbol, pc2.simbol as simbol_a FROM conturi pc LEFT JOIN conturi pc2 ON pc2.simbol like TRIM(pc.simbol)+'%' AND pc.simbol<>pc2.simbol) ca ;
GROUP BY simbol ;
Into cursor crs2
BROW NOWAIT

*Sau
SELECT simbol, COUNT(simbol_a) as NrAnalitice FROM ;
(SELECT pc.simbol, pc2.simbol as simbol_a FROM conturi pc LEFT JOIN conturi pc2 ON pc2.simbol like TRIM(pc.simbol)+'%' AND pc.simbol<>pc2.simbol) ca ;
GROUP BY simbol ;
Into cursor crs3
BROW NOWAIT

*Numai conturile fara analitice
SELECT simbol, Count(simbol_a) as NrAnalitice FROM ;
(SELECT pc.simbol, pc2.simbol as simbol_a FROM conturi pc LEFT JOIN conturi pc2 ON pc2.simbol like TRIM(pc.simbol)+'%' AND pc.simbol<>pc2.simbol) ca ;
GROUP BY simbol HAVING NrAnalitice=0


Daniel Buduru
 11/7/2012 1:12:25 AM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Acum am inteles selectul lui Grig. E Ok. Eu incercasem sa obtin acelasi rezultat fara sa ma folosesc de campurile ID si PARENT_ID, dar se pare ca SQL-ul n-a inteles ce am vrut sa spun:)
Am prins ideea cu  Adjacency list, dar pe moment adaugarea unor campuri suplimentare implica si alte modificari si am incercat sa rezolv problema pe structura existenta.
Pana la urma am reusit cu urmatorul select:

SELECT Simbol FROM Conturi a WHERE RTRIM(Simbol) NOT in (SELECT Simbol FROM Conturi b WHERE b.Simbol#a.Simbol)

 11/7/2012 1:57:43 AM
User is offlineDaniel Buduru
3513 posts
1st




Re: Nomencaltor conturi
 (Romania)
Campurile se adauga doar in planul de conturi, pentru diverse operatii se face un join cu aceasta tabela si se iau de aici id si idparent.
Daca nu vrei sa lucrezi cu ID, poti adauga o singura coloana,  in care treci simbolul contului parent.

Eu am crezut ca esti mai interesat de totalizari, decat de gasirea conturilor fara analitice.

Daniel Buduru
 11/7/2012 11:13:25 PM
User is offlineEugen Gliga
2092 posts
1st




Re: Nomencaltor conturi
 (N/A)
Multumesc pentru solutii. Cand am trimis postul anterior, nu vazusem decat primul tau raspuns. Acum, am vazut ca intre timp ai mai dat niste solutii interesante.
Problema cu modificarile de structura nu e legata de Id sau de numarul de campuri adaugate. Mai exact, eu am o tabela cu toate fisierele din aplicatii si cu structurile lor memorate in campuri memo.Este suficient sa modific structura in acest fisier si  structurile se actualizeaza automat. Partea proasta este ca daca intri cu un program vechi, acesta reface automat vechea structura. Unele fisiere, cum e si planul de conturi este folosit de mai multe aplicatii aflate pe mai multe calculatoare. Deobicei, adun periodic mai multe modificari de structura si recompilez toate programele. Acum lucrez la un program nou care genereaza bilanturi si situatii financiare din fisierele cu balante contabile si prefer sa nu modific structuri. Am avut nevoie in egala masura si de totalizari si de conturi fara analitice, numai ca a doua mi-a iesit mai greu.





  Visual FoxPro  Baze de date, tabele, view-uri si indecsi  Nomencaltor con...

Search  Forum Home         

 Google Ads Minimize

    

Copyright 2002-2013 Profox   Terms Of Use  Privacy Statement