Gộp chuỗi trùng nhau đồng thời cộng số lượng các loại (1 người xem)

Liên hệ QC

Người dùng đang xem chủ đề này

ThaiDieuAnh

Thành viên hoạt động
Tham gia
8/8/16
Bài viết
139
Được thích
24
Nghề nghiệp
Xây dựng
Giả sử em có dữ liệu tại A5 là:
Cocacola: 5; Pepsi: 2; Cam ép Twister: 3
Tại A6 là:
Pepsi: 3; Cam ép Twister: 1; Trà xanh C2: 5
Em muốn một hàm tự tạo có thể gộp những loại tên trùng nhau được phân cách bằng dấu ; và đồng thời cộng số lượng các loại đó. Kết quả trả về sẽ là:
Cocacola: 5; Pepsi: 5; Cam ép Twister: 4; Trà xanh C2: 5
Xin cảm ơn!
 

File đính kèm

Giả sử em có dữ liệu tại A5 là:
Cocacola: 5; Pepsi: 2; Cam ép Twister: 3
Tại A6 là:
Pepsi: 3; Cam ép Twister: 1; Trà xanh C2: 5
Em muốn một hàm tự tạo có thể gộp những loại tên trùng nhau được phân cách bằng dấu ; và đồng thời cộng số lượng các loại đó. Kết quả trả về sẽ là:
Cocacola: 5; Pepsi: 5; Cam ép Twister: 4; Trà xanh C2: 5
Xin cảm ơn!
Bạn chạy code này xem:
Mã:
Sub gop()
Dim i As Long, j As Long, str As String, str2 As String, dic As Object, arr, darr
arr = Range("A5:A" & [A65000].End(xlUp).Row)
ReDim darr(1 To 1000, 1 To 2)
Set dic = CreateObject("scripting.dictionary")
With CreateObject("vbscript.regexp")
    For i = 1 To UBound(arr)
        str = ";" & arr(i, 1)
        .Global = True: .ignorecase = True
        .Pattern = ";\s?([^\;]+:)\s?(\d+)"
        For Each Item In .Execute(str)
            If Not dic.exists(Item.submatches(0)) Then
                j = j + 1
                dic.Add Item.submatches(0), j
                darr(j, 1) = Item.submatches(0): darr(j, 2) = CLng(Item.submatches(1))
            Else
                darr(dic.Item(Item.submatches(0)), 2) = darr(dic.Item(Item.submatches(0)), 2) + CLng(Item.submatches(1))
            End If
        Next
    Next
    For i = 1 To j
        str2 = str2 & darr(i, 1) & " " & darr(i, 2) & IIf(i = j, "", "; ")
    Next
    [c5].Resize(1, 1) = str2
End With
End Sub
 
Upvote 0
Bạn chạy code này xem:
Mã:
Sub gop()
Dim i As Long, j As Long, str As String, str2 As String, dic As Object, arr, darr
arr = Range("A5:A" & [A65000].End(xlUp).Row)
ReDim darr(1 To 1000, 1 To 2)
Set dic = CreateObject("scripting.dictionary")
With CreateObject("vbscript.regexp")
    For i = 1 To UBound(arr)
        str = ";" & arr(i, 1)
        .Global = True: .ignorecase = True
        .Pattern = ";\s?([^\;]+:)\s?(\d+)"
        For Each Item In .Execute(str)
            If Not dic.exists(Item.submatches(0)) Then
                j = j + 1
                dic.Add Item.submatches(0), j
                darr(j, 1) = Item.submatches(0): darr(j, 2) = CLng(Item.submatches(1))
            Else
                darr(dic.Item(Item.submatches(0)), 2) = darr(dic.Item(Item.submatches(0)), 2) + CLng(Item.submatches(1))
            End If
        Next
    Next
    For i = 1 To j
        str2 = str2 & darr(i, 1) & " " & darr(i, 2) & IIf(i = j, "", "; ")
    Next
    [c5].Resize(1, 1) = str2
End With
End Sub
Code chạy chuẩn bác excel_lv1.5 ạ. Tuy nhiên có cách gì thay sub này thành hàm được không bác.
 
Upvote 0
Code chạy chuẩn bác excel_lv1.5 ạ. Tuy nhiên có cách gì thay sub này thành hàm được không bác.
Vậy bạn chỉnh code lại chút:
Mã:
Function gop(rng As Range)
Dim i As Long, j As Long, str As String, str2 As String, dic As Object, arr, darr
arr = rng
ReDim darr(1 To 1000, 1 To 2)
Set dic = CreateObject("scripting.dictionary")
With CreateObject("vbscript.regexp")
    For i = 1 To UBound(arr)
        str = ";" & arr(i, 1)
        .Global = True: .ignorecase = True
        .Pattern = ";\s?([^\;]+:)\s?(\d+)"
        For Each Item In .Execute(str)
            If Not dic.exists(Item.submatches(0)) Then
                j = j + 1
                dic.Add Item.submatches(0), j
                darr(j, 1) = Item.submatches(0): darr(j, 2) = CLng(Item.submatches(1))
            Else
                darr(dic.Item(Item.submatches(0)), 2) = darr(dic.Item(Item.submatches(0)), 2) + CLng(Item.submatches(1))
            End If
        Next
    Next
    For i = 1 To j
        str2 = str2 & darr(i, 1) & " " & darr(i, 2) & IIf(i = j, "", "; ")
    Next
    gop = str2
End With
End Function
Dùng hàm =gop(A5:A6)
 
Upvote 0
Vậy bạn chỉnh code lại chút:
Mã:
Function gop(rng As Range)
Dim i As Long, j As Long, str As String, str2 As String, dic As Object, arr, darr
arr = rng
ReDim darr(1 To 1000, 1 To 2)
Set dic = CreateObject("scripting.dictionary")
With CreateObject("vbscript.regexp")
    For i = 1 To UBound(arr)
        str = ";" & arr(i, 1)
        .Global = True: .ignorecase = True
        .Pattern = ";\s?([^\;]+:)\s?(\d+)"
        For Each Item In .Execute(str)
            If Not dic.exists(Item.submatches(0)) Then
                j = j + 1
                dic.Add Item.submatches(0), j
                darr(j, 1) = Item.submatches(0): darr(j, 2) = CLng(Item.submatches(1))
            Else
                darr(dic.Item(Item.submatches(0)), 2) = darr(dic.Item(Item.submatches(0)), 2) + CLng(Item.submatches(1))
            End If
        Next
    Next
    For i = 1 To j
        str2 = str2 & darr(i, 1) & " " & darr(i, 2) & IIf(i = j, "", "; ")
    Next
    gop = str2
End With
End Function
Dùng hàm =gop(A5:A6)
Khi em dùng hàm = gop(A5) hoặc =gop(A5:A5) thì hàm báo #VALUE!, mà kết quả em mong muốn trong trường hợp này là trả về giá trị ô A5 luôn. Cộng với khi gán công thức trong VBA, chẳng hạn:
Mã:
darr(k, 1) = gop(sArr(i, 2))
thì hàm báo lỗi:
Mã:
ByRef argument type mismatch
Mong các bác giúp đỡ, em xin cảm ơn
 
Upvote 0
Khi em dùng hàm = gop(A5) hoặc =gop(A5:A5) thì hàm báo #VALUE!, mà kết quả em mong muốn trong trường hợp này là trả về giá trị ô A5 luôn. Cộng với khi gán công thức trong VBA, chẳng hạn:
Mã:
darr(k, 1) = gop(sArr(i, 2))
thì hàm báo lỗi:
Mã:
ByRef argument type mismatch
Mong các bác giúp đỡ, em xin cảm ơn
Bạn hiền dùng hàng phổ thông này xem sao
Mã:
Public Function MyJoin(Rng)
Dim SArr, Cll, Tmp, i
SArr = Rng

If IsArray(SArr) = False Then
    MyJoin = Rng
Else
    With CreateObject("Scripting.Dictionary")
    For Each Cll In SArr
        For Each Tmp In Split(Cll, ";")
            Tmp = Split(Tmp, ":")
            .Item(Trim(Tmp(0))) = .Item(Trim(Tmp(0))) + CLng(Trim(Tmp(1)))
        Next Tmp
    Next Cll
    Tmp = .keys()(0) & ": " & .items()(0)
    For i = 1 To .Count - 1
        Tmp = Tmp & "; " & .keys()(i) & ": " & .items()(i)
    Next i
    MyJoin = Tmp
    End With
End If
End Function
 
Lần chỉnh sửa cuối:
Upvote 0
Bạn hiền dùng hàng phổ thông này xem sao
Mã:
Public Function MyJoin(Rng)
Dim SArr, Cll, Tmp, i
SArr = Rng

If IsArray(SArr) = False Then
    MyJoin = Rng
Else
    With CreateObject("Scripting.Dictionary")
    For Each Cll In SArr
        For Each Tmp In Split(Cll, ";")
            Tmp = Split(Tmp, ":")
            .Item(Trim(Tmp(0))) = .Item(Trim(Tmp(0))) + CLng(Trim(Tmp(1)))
        Next Tmp
    Next Cll
    Tmp = .keys()(0) & ": " & .items()(0)
    For i = 1 To .Count - 1
        Tmp = Tmp & "; " & .keys()(i) & ": " & .items()(i)
    Next i
    MyJoin = Tmp
    End With
End If
End Function
Cảm ơn bác, nhưng hàm của bác không chạy được bác ạ
 

File đính kèm

Upvote 0
Upvote 0
Cảm ơn các bác rất rất nhiều ạ, em đang làm cái QLCL cho công ty, theo em biết cái này bác PacificPR rất siêu. Có cách gì nói chuyện riêng được với các bác làm cái này không ạ. Em có rất nhiều thứ muốn trao đổi mà không biết làm thế nào. Mong các bác giúp đỡ
 
Upvote 0
Cảm ơn các bác rất rất nhiều ạ, em đang làm cái QLCL cho công ty, theo em biết cái này bác PacificPR rất siêu. Có cách gì nói chuyện riêng được với các bác làm cái này không ạ. Em có rất nhiều thứ muốn trao đổi mà không biết làm thế nào. Mong các bác giúp đỡ
Bạn lập Topic và đưa cái dự án đó lên mọi người trên diễn đàn sẽ giúp bạn
Mà sao HS QLCL lại liên quan đến CCocacola; Pepsi; Cam ép Twister ... vậy. Hay là cái này để cho cán bộ kỹ thuật giải khát khi làm việc :p
 
Upvote 0
Bạn lập Topic và đưa cái dự án của mình lên mọi người trên diễn đàn sẽ giúp bạn
Mà sao HS QLCL lại liên quan đến CCocacola; Pepsi; Cam ép Twister ... vậy. Hay là cái này để cho cán bộ kỹ thuật giải khát khi làm việc :p
Cảm ơn bác đã quan tâm, cũng vì file bây giờ cũng nhiều dữ liệu mà em chưa quy hoạch được gọn gàng nên nhìn rất rối. Toàn bộ code đều từ GPE + của bác trước đây chia sẻ mà chế tác cho phù hợp với yêu cầu của mình bác ạ. Em đưa file mà toàn coca với pepsi là tương ứng với thiết bị công trình đó bác :p. Bác có mail thì nhắn giúp để em gửi file nhờ bác tý ạ!
 
Upvote 0
Cảm ơn bác đã quan tâm, cũng vì file bây giờ cũng nhiều dữ liệu mà em chưa quy hoạch được gọn gàng nên nhìn rất rối. Toàn bộ code đều từ GPE + của bác trước đây chia sẻ mà chế tác cho phù hợp với yêu cầu của mình bác ạ. Em đưa file mà toàn coca với pepsi là tương ứng với thiết bị công trình đó bác :p. Bác có mail thì nhắn giúp để em gửi file nhờ bác tý ạ!
Gửi lên đây luôn nhiều người làm sẽ có nhiều cách khác nhau. Từ đó bạn sẽ chọn được phương án tối ưu nhất cho mình :D
 
Upvote 0
Web KT

Bài viết mới nhất

Back
Top Bottom