8. Lecke – Több dimenziós tömbök

Több dimenziós tömbök

Két dimenziós tömbök

A előző alkalommal a tömböket egy szekrényhez hasonlítottuk, amin minden egyes polcon van egy értékünk. Azonban képzeljük el, hogy ennek a szekrénynek több oszlopa is lehet, több fakk is lehet egy sorban.

A két dimenziós tömb, kvázi egy táblázatnak felel meg. A polcos képünkkel élve, így képzelhetjük el például:

2 dimenziós tömb

A példában a tömbünk első dimenziójában a tárgy nevek szerepelnek, második dimenziójában pedig a tárgyak színe.

Definiáláskor, egy vesszővel kell elválasztani a dimenziókat.

Dim Tomb(1 To 6, 1 To 2) As Integer

A tömbök definiálsára azonban most mutatok egy egyszerűbb módszert is. Kihagyhatjuk az „1 to” részt a zárójelben, és elég az, ha megadjuk hány értéke lehet a tömbnek:

Dim Tomb(6, 2) As Integer

Egy dimenziós tömb esetén is működik:

Dim Tomb(6) As Integer

Egy elemére hivatkozni,vagy értéket rendelni hozzá az alábbi módon tudunk:

Tomb(1, 1) = Alma
Tomb(1, 2) = zöld

Tomb1(3, 2) = fekete

Példa:

Egy 5×5-as táblázat elemeivel akarunk dolgozni. Egy két dimenziós tömbbe akarjuk felvinni az adatokat. Először nézzünk egy manuális módszert, utána pedig alkalmazzunk egy For ciklusos megoldást.

2 dimenziós tábla példa

Manuálisan:

Sub Makró1()

'Mivel számok és szövegek is vannak benne, így legyen String a típusa
Dim Tablazat1(5, 5) As String

'Eldönthetjük, hogy soronként, vagy oszloponként szeretnénk nézni a táblázatot.
'Azaz ha soronként, akkor az első dimenzióban a különböző emberek lesznek, azaz emberek szerint csoportosítjuk az elemeket,
'De ha oszloponként, akkor adattípusok szerint csoportosítunk. Azaz (1, ... lesz a név; (2, ... lesz az ezres szám; stb.

'Nézük az első verziót, azaz emberenként:

Tablazat1(1, 1) = Béla
Tablazat1(1, 2) = 1000
Tablazat1(1, 3) = 25
Tablazat1(1, 4) = igen
Tablazat1(1, 5) = kék

Tablazat1(2, 1) = Lajos
Tablazat1(2, 2) = 2000
Tablazat1(2, 3) = 30
Tablazat1(2, 4) = nem
Tablazat1(2, 5) = kzöld

Tablazat1(3, 1) = Feri
Tablazat1(3, 2) = 3000
Tablazat1(3, 3) = 35
Tablazat1(3, 4) = nem
Tablazat1(3, 5) = barna

Tablazat1(4, 1) = Gizi
Tablazat1(4, 2) = 4000
Tablazat1(4, 3) = 40
Tablazat1(4, 4) = igen
Tablazat1(4, 5) = kék

Tablazat1(5, 1) = Tibor
Tablazat1(5, 2) = 5000
Tablazat1(5, 3) = 45
Tablazat1(5, 4) = nem
Tablazat1(5, 5) = kék

End Sub

Manuálisan elég hosszú lett a kódunk. Nézzük meg úgy, hogy egy (vagy inkább kettő) ciklus segítségével olvassuk be a táblázatunk celláiból az értékeket.

Sub Makró1()
   'Tehát 5 sorunk és 5 oszlopunk van
   'Vegyünk fel 2 változót, egyikben az sorokat, másikban az oszlopokat fogjuk számolni
   Dim sor As Integer
   Dim oszlop As Integer

   'Definiáljuk a tömbünket
   Dim Tomb(5, 5) As String

   'Egy for ciklus segítségével, megyünk végig a sorokon. Az 1. sortól az 5. sorig.
   For sor = 1 To 5

      'Minden egyes sorban végigmegyünk az adott sor oszlopain is egy For ciklus segítségével.
      'Így kvázi megadjuk az adott cella koordinátáit.
      For oszlop = 1 To 5
         'Tehát 2 ciklus segítségével, minden egyes cellát bejárunk.
         'Ami ide kerül az mind a 25 cellával meg fog történni egymás után.
         'Tehát most a tömbünk aktuális eleméhez az aktuális cella értékét fogjuk rendelni.
         'Ezt az eddig is használt változókkal fogjuk megoldani:
         Tomb(sor, oszlop) = Cells(sor, oszlop).Value
      Next
   Next

   'Teszteljük le, irassuk ki a 4000-ret, ami a 4. sor 2. oszlopban van:
   MsgBox Tomb(4, 2)
End Sub

Ha a zöld megjegyzésektől eltekintünk, akkor azért ez viszonylag rövidebb kód lett. És sokkal szebb is. 🙂

Több dimenziós tömbök

Remélem az előbbi példa nem ijesztett meg, és tudtad követni. Sőt, ha ezt már magadtól is megtudnád csinálni, akkor gratulálok, mert ezzel a programozási tudással bővel el tudsz kezdeni makrókat írni és automatizálni.

Csak említés szintjén, de pár szót beszéljük a több dimenziós tömbökről is. Hiszen az élet nem áll meg 2 dimenziónál. Elméletileg nincs határ, hogy hány dimenziónk lehet, viszont már egy 3 dimenziósat sem könnyű átlátni.

Ezek már inkább adatbázisokra hajaznak. Például egy 3 dimenziós tömböt a szokásos módon definiálunk:

Dim Tomb(10,10,10) as Integer

Az ebben a tömbben tárolt elemek száma 10x10x10, azaz 1000.

Használni nem fogunk ilyen, viszont nem árt ha tudjuk, hogy van ilyen lehetőség is.

Gyakorlati feladat

1. Vegyünk fel az alábbi értékeket egy új táblázatba:
2 dimenziós tömb

2. Tegyük bele az értékeket egy 2 dimenziós tömbbe.
Segítség 1: 9 sorból és 5 oszlopból áll a táblázat, ehhez igazítva hozzuk létre a tömbünket is.
Segítség 2: 2 for ciklus is lesz benne
Segítség 3: A táblázat és a tömb sor koordinátája el van eggyel tolva a fejléc miatt. Így Cells(2,1) lesz egyenlő a tomb(1,1) értékével

Megoldás:

Sub Makró1()
'Meghatározzuk a 2 dimenziós tömbünket, ami egy 9x5-ös táblázatnak felel meg
Dim tomb(9, 5) As String
Dim sor As Integer
Dim oszlop As Integer

'Végigmegyünk a sorokon
For sor = 2 To 10
   'Végigmegyünk az oszlopokon
   For oszlop = 1 To 5
      'Minden cella értékét beletesszük a tömb megfelelő helyére
      'Mivel a táblázat első sora egy fejléc, így nem azonos a cella koordinátája a tömb "koordinátájával"
      'A táblázat 2. sor 1. oszlopa a tömb 1,1 eleme lesz.
      'Ezt a sor változóval is kifejezhetjük, ha mindig kivonunk 1-et.
      tomb(sor - 1, oszlop) = Cells(sor, oszlop).Value
   Next
Next
End Sub

3. Gyakoroljuk az IF elágazást is. Módosítsuk úgy a programunkat, hogy ha a Marketing nyilatkozatnál „igen” szerepel ÉS az elköltött összeg 10.000 forint felett van, akkor a Prémium hírlevél értéke „Küldhető” legyen!
Segítség 1: Kettő IF is lesz benne, ezek egymáson belül lesznek és a cikluson is belül.
Segítség 2: Első IF azt nézi, hogy csak az 5. oszlopban történjen a logikai vizsgálatunk
UPDATE! Segítség 3: Többdimenziós tömbnél gyakran előfordul, hogy az egyes dimenziók más más típusú értékkel bírnak. Például egyik dimenzió egy szám, a másik pedig szöveg. Ennek kiküszöbölését a megoldásban mutatom meg

Megoldás:

Sub Makró1()
Dim tomb(8, 5) As String
'Mivel a táblázatunkban, így a tömbünkben is különböző típusú adatok lesznek, azaz nem csak szöveg hanem szám is, így ezt külön kell tudni kezelnünk. Ha nem kezeljük le és anélkül akarunk műveletek végrehajtani, mondjuk egy olyan tömbbel amit szöveg változóként definiáltunk, akkor értelemszerűen nem fog történni semmi. Tehát egy olyan értéket, ami "Józsi", nem fogunk tudni elosztani 2-vel. Az alábbi módon tudunk vegyes típusú tömböket létrehozni:
Dim vegyestomb   As Variant
vegyestomb = tomb

Dim sor As Integer
Dim oszlop As Integer

For sor = 2 To 9
   For oszlop = 1 To 5
      'Csak az 5. oszlopra legyen érvényes az alábbi feltétel
      If oszlop = 5 Then
         'Ide jön a tényleges feltételünk
         '3. oszlop eleme legyen nagyobb, mint 10000
         '4. oszlop eleme legyen "igen"

         If vegyestomb(sor - 1, 3) > 10000 And vegyestomb(sor - 1, 4) = "igen" Then
            'Ha minden teljesül akkor az 5. oszlop eleme legyen "Küldhető"
            Cells(sor, oszlop).Value = "Küldhető"
         End If
      End If
      'Itt tesszük bele a tömbbe a cella értékét
      vegyestomb(sor - 1, oszlop) = Cells(sor, oszlop).Value

   Next
Next
End Sub

4. Írjuk ki!
G1 cellába ha beírjuk valamelyik sor számát, majd mellette megnyomunk egy gombot, akkor írja ki egy párbeszédablakban, hogy az adott illetőnek lehet e küldeni Prémium hírlevelet, vagy sem. (Pl.: István részére lehet küldeni hírlevelet.”
Segítség 1: ez az előbbiektől már különálló rész lesz a programunkban.

Sub Makró1()

Dim tomb(8, 5) As String
Dim vegyestomb   As Variant
vegyestomb = tomb

Dim sor As Integer
Dim oszlop As Integer

For sor = 2 To 9
   For oszlop = 1 To 5
     If oszlop = 5 Then
        If vegyestomb(sor - 1, 3) > 10000 And vegyestomb(sor - 1, 4) = "igen" Then
            'Ha minden teljesül akkor az 5. oszlop eleme legyen "Küldhető"
            Cells(sor, oszlop).Value = "Küldhető"
         End If
      End If
      vegyestomb(sor - 1, oszlop) = Cells(sor, oszlop).Value
   Next
Next

'KÜLDHETŐ HÍRLEVÉL?
'Létrehozunk egy új változót, ami a G1 cellában megadott sor száma.
Dim kerdeses_sor As Integer
kerdeses_sor = Range("G1").Value

'Először is megvizsgáljuk, hogy a G1 cellában van e megfelelő szám beírva.
If Range("G1").Value > 1 Then
    'Mivel még mindig csúszás van a fejléc miatt, így kell használnunk a -1-et
    If vegyestomb(kerdeses_sor - 1, 5) = "Küldhető" Then
       MsgBox vegyestomb(kerdeses_sor - 1, 2) & " részére lehet küldeni hírlevelet."
    Else
       MsgBox vegyestomb(kerdeses_sor - 1, 2) & " részére NEM lehet küldeni hírlevelet."
    End If
Else
    MsgBox "Írd be a kérdéses sor számát a G' cellába!"
End If

End Sub

Összefoglalás

– Megtanultuk, hogyan tudunk használni egy 2 dimenziós tömböt
– Megnéztük, hogyan tudjuk a táblázatunk értékeit egyszerűen rögzíteni a tömbünkben
– Már tudjuk, hogy egész bonyolult, több dimenziós tömbjeink is lehetnének

Mennyire találtad hasznosnak ezt cikket?
[Összes szavazat: 2 Átlag értékelés: 5]