Tổng quan về Scripting.Dictionary

Chia sẻ bởi:hiepnckh
★★★★★
Quảng cáo

I. Dictionary là gì?

1. Định nghĩa
Là một phần trong thư viện Microsoft Scripting Runtime (scrrun.dll), Dictonary class là một công cụ đầy sức mạnh và linh hoạt. Nó cho phép người sử dụng tạo một object với số lượng item tùy ý,và mỗi item được nhận dạng dựa trên một key duy nhất. Dic có thể nhận các dữ liệu thuộc các kiểu dữ liệu khác nhau mà thường thấy là kiểu chuỗi (string), số (integer, long,…) hay thậm chí là một sự kết hợp giữa cả hai kiểu dữ liệu.

2. Ưu điểm của Dictionary
– Có thể thêm vào số lượng item tùy ý với những kiểu dữ liệu khác nhau.
– Các item và key của Dictionary rất dễ truy xuất, sửa chữa và bổ sung.
– Dictionary cho phép bạn xóa tất cả các item tồn tại trong Dic mà không cần phải phá hủy chính nó.
– Và cuối cùng, các item chỉ có thể được gọi duy nhất bằng cách là thông qua một key mà key đó là bắt buộc và là duy nhất (không thể có 2 key trùng nhau). Điều này tạo thuận lợi cho các bài toán trích lọc danh sách duy nhất và đây cũng chính là ưu điểm lớn nhất của Dictionary.

3. Cách sử dụng Dictionary
1/ Cách khai báo

Vì Dictionary không phải là một phần của thư viện VBA, do đó, để sử dụng nó, chúng ta cần phải khai báo. Bạn có thể khai báo bằng cả hai cách sau:

Cách 1: Để sử dụng cách 1, trước tiên bạn phải vào Tools -> References và lựa chọn Microsoft Scripting Runtime từ trên danh sách để cài đặt -> nhấn OK.
17743
Sau đó, gõ dòng lệnh:

Dim MyDictionary As Scripting.Dictionary
Set MyDictionary = New Scripting.Dictionary

Cách 2: Gõ dòng lệnh:

Dim MyDictionary As Object
Set MyDictionary = CreateObject("Scripting.Dictionary")

Cách 1 sẽ cho tốc độ nhanh hơn cách 2. Tuy nhiên, cách 2 lại thuận tiện hơn cách 1 khi chia sẻ file cho người sử dụng khác, do với máy tính khác nhau sẽ có nhiều người sử dụng các phiên bản khác nhau. Cách 1 chỉ phù hợp khi chính bạn sử dụng, còn cách 2 phù hợp hơn cho việc chia sẻ.

2/ Các phương thức và thuộc tính:
a. Các phương thức:
– Phương thức Add
: Phương thức Add dùng để thêm item vào Dictionary.

MyDictionary.Add Key, Item

Item có nhận dữ liệu thuộc bất kì kiểu dữ liệu gì. Key cũng nhận như item nhưng ngoại trừ kiểu dữ liệu mảng (array). Key phải là duy nhất, nếu bạn thêm item với cùng một key, bạn sẽ gặp lỗi.

– Phương thức Exists: Phương thức Exists sẽ kiểm tra xem Key có tồn tại hay không? Nếu Key tồn tại, kết quả sẽ là True và không tồn tại thì kết quả sẽ là False.

– Phương thức Items: Phương thức Items sẽ trả về giá trị mảng một chiều mà phần tử đầu tiên là phần tử 0 (dù cho bạn có sử dụng Option Base 1).

MyArray = MyDictionary.Items
MsgBox Join(MyArray, ";")

– Phương thức Keys: Phương thức Keys sẽ trả về giá trị mảng một chiều mà phần tử đầu tiên là phần tử 0 (dù cho bạn có sử dụng Option Base 1).

MyArray = MyDictionary.Keys
MsgBox Join(MyArray, ";")

– Phương thức Remove: Phương thức Remove sẽ xóa một item thông qua một Key. Nếu Key không tồn tại, bạn sẽ gặp lỗi.

MyDictionary.Remove "SomeKey"

– Phương thức RemoveAll: Phương thức RemoveAll sẽ xóa toán bộ những gì có trong Dictionary (nhưng không xóa chính nó).

MyDictionary.RemoveAll

b. Các thuộc tính:
– Thuộc tính CompareMode:
Dictionary có thể phân biệt dạng chữ được hay không phụ thuộc vào thuộc tính CompareMode. Giá trị mặc định của thuộc tính là 0 (vbBinaryCompare) giúp phân biệt chữ hoa chữ thường trong Key, còn giá trị 1 (vbTextCompare) thì không phân biệt.

MyDictionary.CompareMode = vbBinaryCompare 'phân biệt
MyDictionary.CompareMode = vbTextCompare 'không phân biệt

Ví dụ dưới đây sẽ không gây ra lỗi, nhưng nếu CompareMode = 1 thì chắc chắn bạn sẽ gặp lỗi vì "gpe" và "GPE" là giống nhau.

With MyDictionary
      .CompareMode = vbBinaryCompare
      .Add "gpe", "lower"
      .Add "GPE", "UPPER"
End With

– Thuộc tính Count: Thuộc tính Count sẽ trả về giá trị số lượng item có trong Dictionary. Nếu không có item trong Dic, thuộc tính này sẽ trả về giá trị 0.

– Thuộc tính Item: Thuộc tính Item giúp truy xuất hoặc thiết lập giá trị cho một Key nào đó.

With MyDictionary
         .Item("SomeKey") = "gpe"
         MsgBox "Giá trị của SomeKey là " & .Item("SomeKey")
End With

Nếu bạn sử dụng thuộc tính Item để đưa một item vào một Key không tồn tại, Dictionary sẽ thêm mới Key không tồn tại đó, đồng thời cũng thêm item vào Key đó luôn. Cũng vậy, nếu bạn truy xuất một item qua một Key không tồn tại, Dictionary sẽ thêm một item rỗng vào chính Key đó. Do đó, sử dụng thuộc tính Item với một Key không tồn tại sẽ không gây ra lỗi.

– Thuộc tính Key: Thuộc tính Key được dùng để thay đổi giá trị của một Key có sẵn. Tuy nhiên, giá trị Key mới phải là giá trị duy nhất trong Dictionary cũng như giá trị Key mà bạn muốn thay đổi cũng phải tồn tại trong Dictionary. Nếu một trong hai điều kiện trên không đúng, chắc chắn lỗi sẽ xảy ra.

MyDictionary.Key("SomeKey") = "SomeOtherKey"

3/ Một số lỗi thường gặp
a. vbBinaryCompare hay vbTextCompare

Mặc định, CompareMode = vbBinaryCompare, tức là "key" "KEY". Còn trong trường hợp ngược lại, "key" = "KEY". Tuy nhiên, cũng chính từ điều này mà đã nảy sinh ra một số rắc rối không cần thiết. Vẫn có nhiều người lẫn lộn giữa vbBinaryCompare và vbTextCompare dẫn đến kết quả không ra như ý muốn. Do đó, bạn cần phải chú ý để thiết lập cho phù hợp.

b. Kiểu dữ liệu của Key

With MyDictionary
         .Add 1, "number"
         .Item("1") = "text"
End With

Dòng số 2, kiểu dữ liệu của Key là dạng số trong khi dòng số 3, kiểu dữ liệu của Key là dạng chuỗi dẫn đến hai Key của ví dụ trên là khác nhau. Muốn cho cả hai Key đó giống nhau cũng như là để gán lại item cho Key, tức chỉ là kiểu chuỗi chẳng hạn, bạn phải sử dụng câu lệnh .Add CStr(1), "number" thay cho dòng số 2 ở bên trên.

4/ Ví dụ tham khảo
Trích từ bài tập của chú Mỹ (ptm0412) trong chuyên đề bài tập VBA. Đây là một dạng khá thông dụng dùng để sử dụng Dic vì mục đích của nó chính là trích lọc ra giá trị duy nhất, tức giá trị "Nhân viên" dùng để biết được nhân viên đó đem lại doanh thu là bao nhiêu.

17744

Sub Cau1()
Dim Dic1 As Object, iRow As Long, i As Long
Dim Arr() As Variant, TmpArr As Variant
With Sheets("Cau1")
.Range("E4:H10").ClearContents
  Set Dic1 = CreateObject("Scripting.Dictionary")
    TmpArr = Sheet1.Range("b2:g21").Value
    ReDim Arr(1 To UBound(TmpArr, 1), 1 To 6)
    For iRow = 1 To UBound(TmpArr, 1)
        If Not IsEmpty(TmpArr(iRow, 2)) And Not Dic1.exists(TmpArr(iRow, 2)) Then
            i = i + 1
             Dic1.Add TmpArr(iRow, 2), i
             Arr(i, 1) = TmpArr(iRow, 1)
             Arr(i, 2) = TmpArr(iRow, 2)
            If TmpArr(iRow, 3) <> "" Then
                Arr(i, 3) = TmpArr(iRow, 6)
            Else
                Arr(i, 4) = TmpArr(iRow, 6)
            End If
        Else
            If TmpArr(iRow, 3) <> "" Then
                Arr(Dic1.Item(TmpArr(iRow, 2)), 3) = Arr(Dic1.Item(TmpArr(iRow, 2)), 3) + TmpArr(iRow, 6)
            Else

Arr(Dic1.Item(TmpArr(iRow, 2)), 4) = Arr(Dic1.Item(TmpArr(iRow, 2)), 4) + TmpArr(iRow, 6)

End If
        End If
    Next iRow
.Range("e4").Resize(i, 4).Value = Arr
End With
End Sub
Xây dựng Lương 3P, KPI cho Doanh nghiệp
Khóa học SprinGO phù hợp

Xây dựng Lương 3P, KPI cho Doanh nghiệp

Làm thế nào để trả lương cho nhân viên chính xác nhất? Đây là một trong những câu hỏi khó trong quản trị nhân...

Xem khóa học
★★★★★ 5 ★ 1 👤 1 ▥ 0
Quảng cáo

Bạn nên đọc

One Response

  1. hiepnckh says:

    II. Một số ứng dụng:
    1. Tạo dãy số ngẫu nhiên không trùng (tác giả ndu96081631)

    Function UniqueRandomNum(Bottom As Long, Top As Long, Amount As Long)
      'Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
      On Error Resume Next
      If Amount > Top - Bottom + 1 Then Amount = Top - Bottom + 1
      With CreateObject("Scripting.Dictionary")
        Do
          .Add Int(Rnd() * (Top - Bottom + 1)) + Bottom, ""
        Loop Until .Count = Amount
        UniqueRandomNum = WorksheetFunction.Transpose(.Keys)
      End With
    End Function

    2. Lọc dữ liệu duy nhất

    Ví dụ ở trên là một minh chứng cho ứng dụng này, bạn có thể đọc ví dụ trên để hiểu rõ hơn, hoặc bạn cũng có thể search trên GPE để tham khảo thêm về cách lọc dữ liệu với độ phức tạp cao hơn.

    3. Ứng dụng game "Quay số trúng thưởng" (tác giả minhthien321)
    Cú pháp hàm: =UniqueRandom(số nhỏ, số lớn, bao nhiêu số cần tạo). Có 2 cách sử dụng, hoặc là dùng trực tiếp trên cell, hoặc là sử dụng VBA.

    4. Loại bỏ kí tự trùng (tác giả ndu96081631)

    Cú pháp hàm: =StrUnique(chuỗi). Có 2 cách sử dụng, hoặc là dùng trực tiếp trên cell, hoặc là sử dụng VBA.

    Function StrUnique(Text As String) As String
      Dim i As Long, Temp
      On Error Resume Next
      If InStr(Text, ",") Then
        Temp = Split(Text, ",")
        With CreateObject("Scripting.Dictionary")
          For i = 0 To UBound(Temp)
            .Add Temp(i), ""
          Next i
          StrUnique = Join(.Keys, ",")
        End With
      Else
        StrUnique = Left(Text, 1)
        For i = 1 To Len(Text)
          If InStr(StrUnique, Mid(Text, i, 1)) = 0 Then StrUnique = StrUnique & Mid(Text, i, 1)
        Next i
      End If
    End Function

    Trên đây chỉ là một số ứng dụng của Dictionary (lẽ dĩ nhiên ứng dụng đó phải có yếu tố giá trị duy nhất). Thực sự thì Dictionary vẫn còn rất nhiều ứng dụng trên nhiều lĩnh vực, tất cả đều phụ thuộc vào nhu cầu cũng như khả năng sáng tạo của chính bạn.

Leave a Reply

Your email address will not be published. Required fields are marked *

Quảng cáo

Cũ vẫn chất

Xem thêm