doanhhoang79
Thành viên hoạt động
- Tham gia
- 31/3/08
- Bài viết
- 142
- Được thích
- 18
Có ai có mẫu tìm kiếm dữ liệu trong Form không? Tôi đang muốn tham khảo
Ai biết chỉ cho tôi với,
Cảm ơn,
Ai biết chỉ cho tôi với,
Cảm ơn,
Thuật toán TÌM KIẾM thì nhiều lắm, chẳng hạn như có thể dùng Find, AutoFilter, Advanced Filter... hoặc các hàm tìm kiếm của Excel...Có ai có mẫu tìm kiếm dữ liệu trong Form không? Tôi đang muốn tham khảo
Ai biết chỉ cho tôi với,
Cảm ơn,
Xem file của bạn, tôi nghĩ nếu nó báo lổi thì chăng qua là do ta chưa khai báo biến mà thôi!Nó báo lỗi ở dòng này:
rg = Sheet1.Range("A1:A10000").Find(UserForm2.ListBox1.List(a - 1, 0)).Row
Cái chính là cái Form của bạn và cơ chế tìm kiếm của bạn không thực tế thôi. Cái Form điều kiện tìm kiếm y chang cái form gốc vậy thì thà tìm luôn trên Form gốc cho nhanh.Mình xin tham gia như sau:
1/Form điều kiện thường nhập tìm mã bắt đầu bằng ký tự gì, có chứa ký tự gì, kết thúc ký tự gì hay đúng mã nào đó.
2/Cơ chế tìm kiếm có 2 dạng:
-Chuyển nhanh đến dòng đầu tiên thỏa mãn điều kiện.
-Lọc và chỉ để lại trên Form những dòng fù hợp, như vậy lựa chọn rất nhanh.
Xem file của bạn, tôi nghĩ nếu nó báo lổi thì chăng qua là do ta chưa khai báo biến mà thôi!
Thử thêm dòng:
Dim rg As Range
Rồi test lại xem!
Ngoài ra hãy thêm dòng:
On Error Resume Next
vào đầu code, phòng trường hợp tìm không thấy sẽ báo lổi
-----------
Tuy nhiên, nhìn mấy Form này thấy nó sao sao ấy ---> Tìm để làm cái gì mới được chứ ---> Sao bạn không đưa file thực tế của bạn lên (file này tôi nghĩ chỉ là giả lập, không thực tế tí nào)
Nếu là tôi thì tôi làm khác ---> Gõ 1 vài ký tự gợi nhớ vào TextBox, bấm nút TÌM, nó sẽ Show vào ListBox những Record có liên quan (giống như tra từ điển ấy) ---> Và đúng như anh Sealand nhận xét, trò này AutoFilter làm ngon lành (chứ ai lại thiết kế ra 2 cái Form kỳ dị như bạn thế kia)Em giải thích thế này:
Giả sử anh có 01 Form1 trong đó có 01 listbox với hàng nghìn dòng dữ liệu. Làm thế nào để anh tìm đến dữ liệu cần tìm một cách nhanh nhất. Anh không thể dò tìm từng dữ liệu, sẽ mất rất nhiều thời gian.
Vì vậy em phải dùng thêm 01 form tìm kiếm với 01 listbox hiện kết quả, sau khi tìm được dữ liệu rồi thì chỉ cần Dblclick vào dữ liệu đó, nó sẽ đưa chỏ chuột đến dữ liệu trong listbox ở Form1. Như vậy sẽ nhanh và pro hơn không???
Nếu là tôi thì tôi làm khác ---> Gõ 1 vài ký tự gợi nhớ vào TextBox, bấm nút TÌM, nó sẽ Show vào ListBox những Record có liên quan (giống như tra từ điển ấy) ---> Và đúng như anh Sealand nhận xét, trò này AutoFilter làm ngon lành (chứ ai lại thiết kế ra 2 cái Form kỳ dị như bạn thế kia)
Để đáp ứng đươc việc lọc với cơ chế chứa 1 vài ký tự gợi ý như Ndu thì ta nên viết sub nạp Item cho List hay Comb chứ không gán đơn giản được. Như vậy, mã nào thỏa mãn thì nạp.
Có 1 cách là RemoveItem không thỏa mãn nhưng khi reset (Hủy lọc) khônglấy lại tất cả các mã được mà chỉ load lại Form mới đwợc
Đây là 1 mẫu vừa làm xong! Bạn thử xem!Em đồng ý quan điểm của các bác,
Các bác có file mẫu cụ thể không gửi em tham khảo với. Lưu ý các tháo tác hoàn toàn thực hiện trên form (không thực hiện ở trong sheet)
Em cảm ơn,
Private Sub TextBox1_Change()
Dim Clls As Range
Application.ScreenUpdating = False
With Sheet1.Range(Sheet1.[A1], Sheet1.[A65536].End(xlUp))
ListBox1.Clear
.AutoFilter 1, TextBox1.Value & "*"
For Each Clls In .Offset(1).SpecialCells(12).SpecialCells(2)
ListBox1.AddItem (Clls)
Next
.AutoFilter
End With
Application.ScreenUpdating = True
End Sub
Đây là 1 mẫu vừa làm xong! Bạn thử xem!
Gọi Form lên, cần tìm cái gì cứ gõ vào TextBox ---> Ví dụ bạn gõ AAB thì lập tức tất cả những mã nào có 3 ký tự đầu là AAB sẽ hiện ra trong ListBox ---> Làm gì nữa tiếp sau đó là tùy bạn
code:
Bạn thấy đấy, thuật toán chính là AutoFilter, phần râu ria còn lại quá đơn giản luôn!PHP:Private Sub TextBox1_Change() Dim Clls As Range Application.ScreenUpdating = False With Sheet1.Range(Sheet1.[A1], Sheet1.[A65536].End(xlUp)) ListBox1.Clear .AutoFilter 1, TextBox1.Value & "*" For Each Clls In .Offset(1).SpecialCells(12).SpecialCells(2) ListBox1.AddItem (Clls) Next .AutoFilter End With Application.ScreenUpdating = True End Sub
Phương pháp của anh ndu rất hay, em sẽ áp dụng vào ứng dụng thực tế của mình,
cảm ơn bác,
Chủ nhật mà bác vẫn vất vả quá nhưng vui bác nhỉ,
Bạn lưu ý : Để việc tìm kiếm hiệu quả hơn, bạn nên thêm phần Sort vào ListBox
Thuật toán về Sort ListBox (hay Sort bất cứ thứ gì) có lẽ ai cũng biết
- Quét qua từng Item
- So sánh Item1 với Item2 ---> Nếu Item1> Item2 thì đổi chổ chúng với nhau
- Và cứ thế tiếp tục
Tuy nhiên phương pháp này làm cho tốc độ tính toán chậm hẳn đi
Trong Excel đã có công cụ Sort, ta tận dụng nó vào code là nhanh nhất...
Thuật toán:
- Lưu vùng dử liệu vào 1 biến tạm
- Sort dử liệu theo trật tự
- Chạy code gì đó (với file của ta là chạy AutoFilter và AddItem vào ListBox)
- Sau khi code xong, lấy biến tạm (đã lưu) áp ngược vào vùng dử liệu (tức trả mọi thứ về như ban đầu)
===> Phương pháp này tỏ ra mạnh về mặt tốc độ nhưng chỉ áp dụng được với vùng dử liệu thô (không chứa công thức)
Bạn thử xem
---------------
Nói thêm 1 chút: Với Form đã tạo như trên, bạn có thể biến nó thành phần mềm tra từ điển được đấy (chỉ cần có Data)
Sửa lại có tí thôi mà (thêm phần Sort vào)Anh Giúp em luôn đi, em còn lơ tơ mơ cái món này lắm,
Cảm ơn anh,
Private Sub TextBox1_Change()
Dim Clls As Range, Temp As Variant
Application.ScreenUpdating = False
With Sheet1.Range(Sheet1.[A1], Sheet1.[A65536].End(xlUp))
Temp = .Value
.Sort .Cells(2, 1), 1, Header:=xlGuess
.AutoFilter 1, TextBox1.Value & "*"
ListBox1.Clear
For Each Clls In .Offset(1).SpecialCells(12).SpecialCells(2)
ListBox1.AddItem (Clls)
Next
.AutoFilter
.Value = Temp
End With
Application.ScreenUpdating = True
End Sub
Vâng... em thấy... và cái này dể sửa mà anh!To Ndu:
Mình cho cách sử lý nạp Comb. của Ndu rất hay. Nhưng có vấn đề 1 chút là nếu gõ ký tự không có dòng nào thỏa thì nó nạp tất cả (Thậm chí cả tiêu đề, nếu có vài cột nưa có cũng nạp tất). Bạn hiệu chỉnh chút nữa cho hoàn thiện.
P/S:Mình tham gia cách "bình dân" nhất (Ý mình nói là không sử dụng chức năng nâng cao của Exc)
Vâng... em thấy... và cái này dể sửa mà anh!
Thêm đoạn:
If Len(Trim(TextBox1.Value)) = 0 Then Exit Sub
vào đầu code!
Thay đoạn:
For Each Clls In .Offset(1).SpecialCells(12).SpecialCells(2)
thành:
For Each Clls In .Offset(1).SpecialCells(12)
===> Vậy là xong!
Vòng lập For duyệt qua các cell đã được Filter sẽ nhanh hơn rất nhiều so với duyệt qua toàn bộ ---> Điều này dể nhận thấy khi anh gõ nhiều ký tự vào khung tìm kiếm
Em lấy ví dụ:
- Khi em gõ chữ ABB thì qua bộ lọc AutoFilter, số dòng dử liệu chỉ còn lại 4, tương đương vòng lập For sẽ chỉ duyệt qua 4 lần... Trong khi đó với code của anh nó vẫn phải duyệt 500 lần
File ở bài số #19 của anh Sealand là dạng ListBox với 2 cột đấy, bạn tải về mà nghiên cứu ---> Tôi nghĩ rất dể (mò tí là ra)Các bác cho em hỏi nếu muốn hiển thị nhiều cột ở trong ListBox thì làm thế nào nhỉ?
DIỄN ĐÀN GIẢI PHÁP EXCEL Group 1
DIỄN ĐÀN GIẢI PHÁP EXCEL Group 2