Live-Forum - Die aktuellen Beiträge
Anzeige
Archiv - Navigation
1732to1736
Aktuelles Verzeichnis
Verzeichnis Index
Übersicht Verzeichnisse
Vorheriger Thread
Rückwärts Blättern
Nächster Thread
Vorwärts blättern
Anzeige
HERBERS
Excel-Forum (Archiv)
20+ Jahre Excel-Kompetenz: Von Anwendern, für Anwender
Inhaltsverzeichnis

Listbox schnell mit vielen Einträgen füllen

Listbox schnell mit vielen Einträgen füllen
20.01.2020 07:15:15
Klaus
Hallo VBA-Profis,
ich suche eine Möglichkeit, eine Listbox sehr schnell mit vielen Einträgen zu füllen.
Hintergrund: Ich habe in einer Userform eine TextBox1. Bei jeder Änderung der TextBox1 möchte ich, dass ListBox1 geleert und dann mit allen Einträgen %like% TextBox1 gefüllt wird.
Die Einträge kommen aus einer Access Datenbank.
Momentan funktioniert es so:

Sub Listbox_SQL(mySql As String)
On Error GoTo hell
Dim t
t = Timer
Const pfad As String = "C:\Pfad"          'Access DB PFad
Const myAccessDB As String = "MyAccDB.mdb"                'Access DB Dateiname
Const APPNAME = "mod_Access / Gefilter_laden_SQL"
'ACCESS Tabelle per SQL Kommando filtern und gefilterte laden
Dim cmd As ADODB.Command
Dim con As ADODB.Connection
Dim rs As ADODB.Recordset
Dim spalte As Long
Debug.Print "DIM after: " & Timer - t
Set con = New ADODB.Connection
con.Open ConnectionString:= _
"Provider=Microsoft.ACE.OLEDB.12.0;" & _
"Data Source=" & pfad & "\" & myAccessDB & ";" & _
"Mode=Share Exclusive"
Set cmd = New ADODB.Command
cmd.ActiveConnection = con
Set rs = New ADODB.Recordset
rs.CursorLocation = adUseServer
'rs.Index = "Primarykey"
Debug.Print "SET Con after: " & Timer - t
rs.Open mySql, _
ActiveConnection:=con, _
CursorType:=adOpenStatic, _
LockType:=adLockPessimistic, _
Options:=adCmdTableDirect
Debug.Print "RS after: " & Timer - t
UF_Wahl.ListBox1.Clear
If Not rs.BOF Or rs.EOF Then
rs.MoveFirst
Do While Not rs.EOF
UF_Wahl.ListBox1.AddItem rs.Fields(0).Value
rs.MoveNext
Loop
End If
Debug.Print "Listbox after: " & Timer - t
'*** Fehlerbehandlung
hell:
If Err.Number = -2147467259 Then Resume     'Datenbank wird bereits verwendet
Err.Clear
Set cmd = Nothing
con.Close
Set con = Nothing
End Sub
Private Sub TextBox_Model_Change()
Call Listbox_SQL("Select Tier from Tierreich as mytab where [mytab.Tier] like '%" & UF_Wahl. _
TextBox_Model & "%'")
End Sub
'DIM after: 0
'SET Con after: 0,125
'RS after: 0,4375
'Listbox after: 1,109375
Wie ihr seht, dauert das füllen der Listbox (es sind etwas über 1000 Einträge) über 0,6 sekunden. Das klingt wenig, ist aber extrem störend wenn in TextBox1 getippt wird.
Gibt es eine Möglichkeit, die Listbox schneller und möglichst ohne Schleife komplett zu füllen? Bis dahin behelfe ich mir damit, das Makro auf "TextBox1_Exit" statt "_change" zu legen, finde es aber nur halb so elegant.
LG,
Klaus M.

12
Beiträge zum Forumthread
Beiträge zu diesem Forumthread

Betreff
Datum
Anwender
Anzeige
AW: Listbox schnell mit vielen Einträgen füllen
20.01.2020 07:52:59
Daniel
Hi
Das befüllen der Listbox könnte schneller gehen, wenn der vollständige Inhalt in einem 1- oder 2-Dimensionalen Array bereit steht. Dann reicht:
Listbox1.List = DeinArray
Gruß Daniel
AW: Listbox schnell mit vielen Einträgen füllen
20.01.2020 08:02:05
Klaus
Hallo Daniel,
danke für die schnelle Antwort. Wie bekomme ich die Access ADOB.Recordset denn am schnellsten in ein Array - oder ist rs bereits das Array?
LG,
Klaus M.
AW: Listbox schnell mit vielen Einträgen füllen
20.01.2020 08:10:12
Daniel
Keine Ahnung.
Mit den ADODB-Funktionen kennen ich mich nicht aus.
Da hast du mehr Ahnung als ich.
Gruß Daniel
Array schnell mit ADOB.Recordset füllen
20.01.2020 08:41:03
Klaus
Hallo Daniel,
danke schonmal für deine Hilfe - das Beschreiben der Listbox per Array geht rasend schnell, aber das beschreiben des Arrays per Schleife aus dem Recordset dauert genauso lange, als wenn ich es direkt in die Listbox schreibe.
Ich stelle mal auf offen, in der Hoffnung dass sich jemand mit ADOB.Recordset auskennt.
    Dim MyArr(1000) As String
Dim i As Long
i = 0
UF_Wahl.ListBox1.Clear
If Not rs.BOF Or rs.EOF Then
rs.MoveFirst
Do While Not rs.EOF
'UF_Wahl.ListBox1.AddItem rs.Fields(0).Value
MyArr(i) = rs.Fields(0).Value
i = i + 1
rs.MoveNext
Loop
End If
UF_Wahl.ListBox1.List = MyArr()
LG,
Klaus M.
Anzeige
AW: Array schnell mit ADOB.Recordset füllen
20.01.2020 08:44:02
Klaus
Wenn ich RS in ein Tabellenblatt schreibe geht es rasend schnell, selbst wenn rs tausende Einträge hat:
  Tabelle1.Range("A1").CopyFromRecordset Data:=rs
Wenn ich mit "CopyFromRecordset" direkt in ein Array schreiben könnte, wäre mein Problem gelöst. Bekomme es leider nicht hin, "myArr = CopyFromRecordset Data:=rs" geht natürlich nicht.
LG,
Klaus M.
Du könntest es...
20.01.2020 08:48:57
Case
Hallo, :-)
... mal so probieren: ;-)
Dim varArr As Variant
varArr = rs.GetRows
ListBox1.List = varArr
Servus
Case

Anzeige
AW: Du könntest es...
20.01.2020 09:12:36
Klaus
Hallo Case,
leider nein - dies schreibt mir nur den ersten (oder den nullten?) Eintrag in die Listbox, aber keine weiteren.
LG,
Klaus M.
AW: Du könntest es...
20.01.2020 14:35:28
Luschi
Hallo Klaus,
wenn ich mir Deine Technologie so anschaue, dann willst Du bei jedem Tastenschlag in der TextBox folgendes machen:
- AdoDB-Connection definieren und öffnen
- Recordset definieren
- diese beiden Sachen gehören da nicht hin
- sondern in das Ereignis 'Initialisieren der Userform'
- denn es wird ja die Datenquelle während der gesamten Zeit nicht gewechselt
- das Schließen der AdoDB-Connection und des Recordsets
  kommt in das Ereignis 'Schließen der Userform' (Terminate)
- damit ist schon mal sehr viel Zeit gewonnen durch das nicht
  immer wiederkehrende Öffnen/Schließen der Datenquelle
- ich habe im I-Net ein VB-Script gefunden
  wie man 1 Recordset in ein Array umschaufelt
- teste es gerade in Vba und 1er Access-DB
- also noch ein bißchen Geduld
Gruß von Luschi
aus klein-Paris
Anzeige
AW: Du könntest es...
20.01.2020 17:30:22
Klaus
Luschi,
Öffnen / Schließen der ADOB Connection in Initialise und Close zu verlagern ist eine gute Idee - das ist auf jedem Fall sauberer. Ich habe überhaupt nicht darüber nachgedacht und ganz Script-Kiddie mäßig das vorhanden SQL-Script kopiert und benutzt wie es ist.
Aber es wird nicht helfen - die Recordsets laden dauert ja nur eine zehntel Sekunde, das langsame an dem ganzen Vorgang ist die Schleife zum befüllen der Listbox. Ich warte aber ganz geduldig auf dein Array-Script :-)
Offtopic: Ich benutze die ADOB-Connection Makros eigentlich immer so:
sub hochladen()
for i = 1 to 1000
call AccessMakro(i)
next i
end sub
sub Accesmakro(i as long)
recordset erstellen
rs!eintrag = cells(i,1).value
recordset schließen
end sub

Also Adob auf / zu / auf / zu und das tausend mal. Ist trotzdem rasend schnell! Wenn es deutlich mehr als 5000 Einträge werden, nehme ich aber ein optimiertes Makro.
LG,
Klaus M.
Anzeige
AW: Du könntest es...
21.01.2020 13:52:39
Klaus
Hallo Luschi,
ich habe zwar jetzt eine 1a Lösung von Daniel, aber aus rein akademischen Gründen wäre ich an deiner Lösung trotzdem interessiert! :-)
LG,
Klaus M.
AW: Listbox schnell mit vielen Einträgen füllen
20.01.2020 17:56:05
Daniel
Hi
wie veränderlich ist denn die Datenbank?
ggf ist es schneller, wenn du einmalig (z.B. im Initialize-Event der Userform) alle Daten in ein eindimensionales Array schreibst und dann für die Befüllung der Listbox die FILTER-Funktion verwendest:
Listbox1.List = Filter(ArrayVollständig, Textbox1.Text, True)
Gruß Daniel
AW: Listbox schnell mit vielen Einträgen füllen
21.01.2020 08:43:55
Klaus
genial. Mega schnell. FETTES DANKE an Daniel!
LG,
Klaus M.

Links zu Excel-Dialogen

Beliebteste Forumthreads (12 Monate)

Anzeige

Beliebteste Forumthreads (12 Monate)

Anzeige
Anzeige
Anzeige