我有一個需求是將某欄的資料複製到其他地方, 但是希望能夠是按照大小排列, 並且過濾掉重複的資料
我先做一個測試, 如果我在A1輸入自訂函數(MyCopy), 去改變B1儲存格的內容 :
結果是 #VALUE!(失敗), 再將程式修改一下, 在A1中輸入 =MyCopy(B1), 把B1當參數傳進去會怎樣
結果依然是 #VALUE!(失敗), 只好爬文看看別人的作法, 爬了很久直到這篇文章(How to Change Another Cell with a VBA Function), 作者的技巧是用 Evaluate 函數來叫另一個自訂函數來幫忙修改其他儲存格的資料, 看來自訂函數果真無法直接修改其他儲存格的資料了!(如果有其他作法也歡迎留言告知喔), 程式再改一下測測看
我在A1儲存格中輸入 =MyCopy(), 結果對了!!(附上圖慶祝一下)
再來是排序問題, 網路上作法很多, 最後我挑了 System.Collections.SortedList 這個物件, 程式如下 :
結果還不錯, 嘗試修改A1..B6中的資料也會即時改變, 可是發現這有一個問題, 就是當我把A5的AA文字刪除後, 會變成下面畫面 :
結果會出現兩個資料D, 原因是當不重複資料總數減少時, 程式寫完結果並不會繼續清除下面之前的舊資料!! 由此可知一個真正完整不被人罵的程式要處理很多問題, 一個簡單的程式會變成很巨大, 所以我來處理這個問題看看:
雖然解決了這個問題, 但是感覺處理的不是很好, 如果有好的想法歡迎留言喔! ^ ^
Function MyCopy() As Variant
Cells(1, 2).Value = "AA"
MyCopy = "OK"
End Function
結果是 #VALUE!(失敗), 再將程式修改一下, 在A1中輸入 =MyCopy(B1), 把B1當參數傳進去會怎樣
Function MyCopy(myRange As Range) As Variant
myRange.Value = "AA"
MyCopy = "OK"
End Function
結果依然是 #VALUE!(失敗), 只好爬文看看別人的作法, 爬了很久直到這篇文章(How to Change Another Cell with a VBA Function), 作者的技巧是用 Evaluate 函數來叫另一個自訂函數來幫忙修改其他儲存格的資料, 看來自訂函數果真無法直接修改其他儲存格的資料了!(如果有其他作法也歡迎留言告知喔), 程式再改一下測測看
Function MyCopy() As Variant
Evaluate "MyChange(B1,100)"
MyCopy = "OK"
End Function
Function MyChange(myRange As Range, newData As Variant)
myRange.Value = newData
End Function
我在A1儲存格中輸入 =MyCopy(), 結果對了!!(附上圖慶祝一下)
再來是排序問題, 網路上作法很多, 最後我挑了 System.Collections.SortedList 這個物件, 程式如下 :
Function MyCopy(copyFrom As Range, copyTo As Range) As Variant
Dim mList As Object
Dim i As Integer
Dim data As Variant
Set mList = CreateObject("System.Collections.SortedList") '建立排序物件
'開始排序並且濾掉重複資料
For Each data In copyFrom
If data.Value <> "" Then
'非空白的才處理
If Not mList.ContainsKey(data.Value) Then
mList.Add data.Value, "" '新增
End If
End If
Next
i = 1
'開始寫到新的位置
For Each data In copyTo
If i <= mList.Count Then
'改變其他儲存格的方法
Evaluate "MyChange(" + data.Address + ",""" + mList.GetKey(i - 1) + """)"
Else
Exit For
End If
i = i + 1
Next
MyCopy = "OK"
End Function
'改變其他儲存格的自訂函數
Function MyChange(myRange As Range, newData As Variant)
myRange.Value = newData
End Function
結果還不錯, 嘗試修改A1..B6中的資料也會即時改變, 可是發現這有一個問題, 就是當我把A5的AA文字刪除後, 會變成下面畫面 :
結果會出現兩個資料D, 原因是當不重複資料總數減少時, 程式寫完結果並不會繼續清除下面之前的舊資料!! 由此可知一個真正完整不被人罵的程式要處理很多問題, 一個簡單的程式會變成很巨大, 所以我來處理這個問題看看:
Function MyCopy(copyFrom As Range, copyTo As Range) As Variant
Dim mList As Object
Dim i As Integer
Dim data As Variant
Set mList = CreateObject("System.Collections.SortedList") '建立排序物件
'開始排序並且濾掉重複資料
For Each data In copyFrom
If data.Value <> "" Then
'非空白的才處理
If Not mList.ContainsKey(data.Value) Then
mList.Add data.Value, "" '新增
End If
End If
Next
i = 1
'開始寫到新的位置
For Each data In copyTo
If i <= mList.Count Then
'改變其他儲存格的方法
Evaluate "MyChange(" + data.Address + ",""" + mList.GetKey(i - 1) + """)"
Else
If data.Value <> "" Then
'非空白的才處理
Evaluate "MyChange(" + data.Address + ","""")"
Else
Exit For
End If
End If
i = i + 1
Next
MyCopy = "OK"
End Function
'改變其他儲存格的自訂函數
Function MyChange(myRange As Range, newData As Variant)
myRange.Value = newData
End Function
雖然解決了這個問題, 但是感覺處理的不是很好, 如果有好的想法歡迎留言喔! ^ ^
測試時間: 2020年07月30日
測試環境: Windows 10 家用版, Excel 2019 家用版



留言
張貼留言