Az „Excel” fórum célja, hogy keretet adjon az Excel felhasználók széles táborának tapasztalataik megosztására, és lehetőséget a segítséget kérőknek. Az alábbi összefoglaló azért készült, hogy segítse a helyes kérdésfeltevést.
– Írd le szabatosan a problémát. Úgy fogalmazz, hogy ne csak te magad, de a szakértő is megértse, mire szeretnél választ kapni.
– Írd le, hogy milyen verziójú Excellel dolgozol. (Vagy ha nem – ill. nem csak – Excel, akkor micsoda?)
– Írd le, hogy milyen úton indultál el, és hol akadtál el rajta.
– A kérdés megértése szempontjából sokat segíthet, ha feltölteszt egy képet, amin látszik, hogy mit szeretnél, vagy illusztrálja azt.
– Még jobb, ha feltöltesz egy minta munkafüzetet valahová (pl. data.hu). Feltöltés előtt távolítsd el belőle a nem publikus adatokat.
– Ha a feladat jellege olyan, célszerű az "előtte" és "utána" állapotokat bemutatni. (Miből kellene csinálni mit?)
– Ha VBA kódon kell javítani, másold be a releváns kódrészt. Rövid kód mehet hozzászólásba, hosszú kód inkább ide: http://pastebin.com/
– Ha valami nem úgy működik, ahogy kellene, add meg a rendellenes viselkedés jellemzőit, a hibaüzenetet, és a hibát okozó programsort.
Delila kösz, ki fogom próbálni. Bár az igazat megvallva, nem tudom, hogy akkor is jelentkezik-e a hiba, amikor a hibaüzenetet ki kell írni. Halvány emlékeim szerint a megállás akkor jelentkezett, amikor egyáltalán nem kellett az eltérésre figyelmeztetni. (Szándékom szerint egyébként is ez volt a részlet funkciója. Hiszen, ha tucatjával jönnek az eltérések, akkkor úgyis valami generális hiba van. Én meg azt ellenőriztem, hogy nincs-e valami apró poloska, ami egy-két rejtett hibát okoz a 2500 sor egyenként közel 20-20 adatában. Így a jellemző eset az, amikor a programrész hibajelzés nélkül fut le.)
Kreálsz egy új oszlopot, és abba képlettel összefűzöd a 4 oszlop tartalmát, ami sorbarendezezési szempont, a prioritás szerinti sorrendben. Tehát ha pl. A, D, B, K oszlopok szerint akarsz sorbarendezni, akkor X segédoszlop tartalma:
X2 = A2 & D2 & B2 & K2
Ezután rendezed az egészet X oszlop szerint, majd törlöd az X oszlopot.
Ha valamelyik oszlopban számok vannak, akkor ott még kell egy furfang: át kell alakítani a számokat helyiértéket megőrző szöveggé. Ha pl. a fenti példában D oszlopban számok vannak, és egyik szám sem nagyobb, mint 10^16, akkor
Nem a kérdésedre válaszolok, de arra, hogy a felhasználó "ne unatkozzon", van egy másik mód is, mint az msgbox.
Kiírathatod a státuszsorba a program pillanatnyi állását, vagy bármilyen más szöveget.
For sor = 1 To sorok adat1 = adat1 = Sheets(aktlapnév).Cells(sor, oszlop) adat2 = adat2 = Workbooks(ellfile).Sheets(aktlapnév).Cells(sor, oszlop) If adat1 <> adat2 Then Application.StatusBar = Str(sor) + ". sor, " + oszlopnév(oszlop) + ". oszlop eltér!" End If Next Application.StatusBar = False
Az utolsó sor visszaállítja a státuszsor eredeti beállítását.
Sem a magyarázatát, sem a megoldását nem tudom, de azt igen, hogy nem különleges eset. Egy-egy hosszabb programfutás során nálam is gyakran előfordul, hogy kvázi "lefagy" az Excel, de közben valójában tekeri a CPU-t ezerrel, és számolja, mait számolni kell, csak megszakad a kapcsolata a külvilággal. Úgy vettem észre, hogy a fókuszváltás az ablakok közt (pl. az Excel ablak elveszti a fókuszt) gyakran (talán mindig) kiváltja ezt a viselkedést. De ha megszakítom a program futását egy Ctrl+Break -kel, majd azt modnom neki, hogy folytassa, visszaáll a megszokott működés.
Az egész valószínűleg egy rosszul megírt Microsoft termék hibája. Mivel a makród ettől még rendesen lefut, a helyedben nem nyugtalankodnék nagyon. Viszont érdemes a makródat úgy megírni, hogy az időigényes számolási rész előtt tegyen ki a usernek egy kis cédulát, amin az áll, hogy hosszú folyamat jön, ami alatt az Excel esetleg úgy tűnhet, mintha lefagyott volna, de legyen türelemmel, és ne piszkálja a Ctrl+Alt+Del gombokat.
Van 2500 sornyi adatom, ezen belül 16 oszlop (A-P). Ezeket tartalmazza a sor és az oszlop változó az alábbi részletben, ahol ellenőrzést végzek, hogy azonos-e a két fájl összes adata.
Közben, hogy a felhasználó (szerencsére ez itt csak magam vagyok, hiszen a programot tesztelem) ne unatkozzon, minden sor vizsgálatának elején ráállok annak 1. oszlopára: (Cells(sor, 1).Select). Így a vizsgálat közben szépen fut lefelé a képernyő.
For sor = 1 To sorok
Cells(sor, 1).Select ' Hogy lássuk, amint megy a sorokon
Ez egy nagyon egyszerű programrészlet. Nem is lenne gondom vele. De számomra érthetetlen okokból időnként megáll a képernyőn a futás. A program dolgozik ugyan, de valamelyik sor kiírásánál megmerevedik a képernyő. Azaz látszólag nem hajtja végre a Cells(sor, 1).Select parancsot.
Ráadásul a jelenség nem következetes. Van amikor rendesen lefut, van amikor valamelyik soron megáll a léptetés. És, hogy melyiken, az mindig változó. Valami memóriazavar lehet, úgy sejtem.
Aztán – ha megállt a képernyőn a léptetés - a program befejezi azért az ellenőrzést, és kiírja a program végén, hogy vége az ellenőrzésnek (vagy ha közben eltérés van, azaz ki kell írni a hibát, hogy eltérnek az adatok, akkor azt is rendesen megteszi.), tehát csak a Cells(sor, 1).Select parancs nem működik. Szerencsére nincs jelentősége, mert a felhasználó nem találkozik vele, csak engem nyugtalanít. Mint minden olyan esemény, ahol nem az történik, amit szeretnék Ismeritek Murphy idevágó törvényét: „A program mindig az utasításaidat hajtja végre, nem pedig a kívánságaidat”.
Szóval tudja valaki a dolog magyarázatát, esetleg a megoldását?
Dehogynem, rengeteg. De a többségét megoldom. Amit nem, abban eddig segítettetek. Most úgy látom több mint 3 hónap után, hogy a programom átadható a felhasználónak. Kösz az eddigieket is.
De azért még dolgozom tovább. Sejtésem szerint az Excel programozás lehetőségeinek talán vagy fél százalékát megismertem:-))). De hogy ebből mikor lesz akár 25%, az a messzi jövő kérdése:-(((
Pl. Használhatod a ComboBox Change eseménykezelőjét:
Private Sub ComboBox1_Change() If Me.ComboBox1.Text <> "" Then Me.Label1.Caption = "A ComboBox értéke NEM üres" Else: Me.Label1.Caption = "A ComboBox most üres" End If End Sub
Mivel a MIN és MAX függvényekkel [=MIN(A1:L47) és =MAX(A1:L47)] sikerül kideríteni, hogy a tartomány legkisebb tagja 1, a legnagyobb 111, egy új oszlopba felvesszük 1-től 111-ig a sorszámokat. Legyen most ez a tartomány az N1:N111.
Az O1 cella képlete: =DARABTELI($A$1:$L$47;N1). Ezt lemásolod az O111 celláig, és kész.
"Megspórolhatod" az N oszlopot, ha egy oszlopba az első sorba a =DARABTELI($A$1:$L$47;SOR()) képletet írod a fenti helyett, és ezt másolod le a 111. sorig. A SOR() függvény az aktuális sor számát adja eredményül, nem kell egy másik oszlopban lévő sorszámra hivatkoznia a DARABTELI függvénynek.
Akkor mondok egy nagyon primitív megoldást. Azt meg tudod tenni, hogy valamennyi oszlop adatát egyenként kijelölöd, és egyenként átmásolod az A oszlop adatai mögé? Ha igen, akkor az átmásolgatás után az A oszlopban lesz 564 adatod, tekintve, hogy most van 12 oszlopod, egyenként 47 sorral. (Megjegyzés: Az átmásolásnál javaslom a kivágás/beillesztést, így nehezebb eltéveszteni, hogy hol tartasz)
Ezután az A oszlop 564 adatát (vagy az egész A oszlopot) kijelölöd (a kijelölés muszáj az adatok közt lévő szóközök miatt), és adatok->sorba rendezés>A oszlop->emelkedő sorrendben.
Ez már összehozza az azonos értékeket, és meg tudod számolni őket.
A szakértőktől elnézést a megoldás közönségessége miatt, de működik, és talán érthető.