Guten morgen zusammen,
ich habe nachstehendes Problem:
Ich erstelle eine Datenbank für eine Turnierverwaltung. Es gibt eine Tabelle "Turnier" in der die Teilnehmer und deren Ergebisse verwaltet werden. Hierunter sind u.a. die Felder "Summe Runden" und "Rangber".
Über eine Abfrage werden bestimmte Klassen und Gruppen gefiltert. Die Abfrage heißt ABF_Urkunden. Ich möchte nun das Feld "Rangber" automatisch mit dem entsprechenden Rang füllen um Urkunden drucken zu können. Dazu habe ich nachstehende Funktion gefunden:
Public Function RangSetzen()
Dim db As Database
Dim rs As Recordset
Dim z As Long
Set db = CurrentDb()
Set rs = db.openrecordset("SELECT * FROM ABF_Urkunden ORDER BY [Summe Runden];", dbopendynaset)
Do Until rs.EOF
z = z + 1
rs.Edit
rs!Rangber = z
rs.Update
rs.MoveNext
Loop
rs.Close
db.Close
End Function
Über eine Schaltfläche im Hauptformular wird die Berechnung durchgeführt um im Unterformular die neu berechnete Abfrage zu zeigen.
Dim a As Variant
a = RangSetzen()
MsgBox "VBA-Aktualisierung wurde durchgeführt!", 48
Me.Requery
Beim Ausführen erhalte ich die nachstehende Fehlermeldung:
Laufzeitfehler 3061
Es wurden 4 Parameter erwartet, aber es wurden zuwenig Parameter übergeben.
Kann mir bitte jemand helfen ? Ich nutze Access 2010
Vielen Dank
Die Fehlermeldung ist typisch für nicht verfügbare Felder und Tabellen/Abfragen sowie für nicht auflösbare Parameter (Formularbezüge?).
Wie lautet die vollständige SQL-Anweisung zu ABF_Urkunden?
Danke dass Du dir das anschaust. Hier der Code für die Abfrage:
SELECT Turnier.Turniername, Turnier.Teilnehmer, Turnier.[Summe Runden], Turnier.[Summe X], Turnier.Klasse_Grob_FS, Turnier.Bogenklasse_FS, Turnier.Altersklasse_FS, Turnier.Rangber
FROM Turnier
WHERE (((Turnier.Turniername)=[Formulare]![Hauptmenü]![Auswahl_Turnier]) AND ((Turnier.Klasse_Grob_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld1]) AND ((Turnier.Bogenklasse_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld3]) AND ((Turnier.Altersklasse_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld5]))
ORDER BY Turnier.[Summe Runden] DESC;
Kann es sein, das die Funktion nicht in eine Abfrage schreiben kann ?
Du verwendest in Deiner Abfrage direkte Formularbezüge in der Filterung. Die sind schnell mal kritisch. Wenn Du die Abfrage in Access öffnest (Doppelklick im Navigationsbereich, OpenQuery u.a.), dann spielt Access mit und macht die Werte der Formularfelder verfügbar.
In Deiner Funktion wird die Abfrage jedoch direkt an die Jet-Engine übergeben (über das Recordset). Diese kennt keine Formulare und deren Objekte und kann so den Inhalt nicht auswerten. Da kommt dann eben die Nachfrage.
Siehe auch Ein Parameter wurde erwartet (http://www.donkarl.com?FAQ6.4)
Da gibt es auch Lösungsvorschläge (Eval, echte Parameterabfrage).
Eine weitere Möglichkeit wäre, unmittelbar die SQL-Anweisung der Abfrage einzusetzen und die Parameter dynamisch einzusetzen, wobei die Parameter sinnvollerweise als Argumente an die Funktion zu übergeben wären, etwa ...
Public Function RangSetzen(ByVal Arg1 As String, ...)
Dim sSQL As String
' ...
sSQL = "SELECT * FROM Turnier" & _
" WHERE Turniername = '" & Arg1 & "' AND Klasse_Grob_FS = ..."
Set rs = db.Openrecordset(sSQL, dbOpenDynaset)
' ...
End Function
Hier werden die Variablen/Argumente vor dem Zusammensetzen der SQL-Anweisung ausgewertet, so dass dann die SQL-Anweisung fertig an die Jet-Engine übergeben wird.
Alternativ könnte man auch an eine komplette Abfragelösung denken: Laufende Nummer/Summe in Abfragen (http://www.donkarl.com?FAQ3.11)
Vielen Dank.
An die angesprochene Lösung habe ich auch schon gedacht.
Wie baue ich diese denn in die ABF_Urkunden ein ? Einfach hinten anfügen ?
SELECT Turnier.Turniername, Turnier.Teilnehmer, Turnier.[Summe Runden], Turnier.[Summe X], Turnier.Klasse_Grob_FS, Turnier.Bogenklasse_FS, Turnier.Altersklasse_FS, Turnier.Rangber
FROM Turnier
WHERE (((Turnier.Turniername)=[Formulare]![Hauptmenü]![Auswahl_Turnier]) AND ((Turnier.Klasse_Grob_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld1]) AND ((Turnier.Bogenklasse_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld3]) AND ((Turnier.Altersklasse_FS)=[Formulare]![FRM_Urkunden]![Kombinationsfeld5]))
ORDER BY Turnier.[Summe Runden] DESC;
und dann
LaufNummer: (Select Count (*) FROM [ABF_Urkunden] as Temp WHERE [Temp].[Summe Runden] < [ABF_Urkunden].[Summe Runden])+1
Wenn ich das mache kommt es zu einem Zirkelbezug
Danke Michael
Hi,
du musst dich im Sub-Select auf die Tabelle "Turnier" beziehen.
PS:
Diese Art der Rangermittlung ist deiner Prozedur schon deshalb vorzuziehen, weil dabei gleiche Ergebnisse und somit auch gleriche Plätze berücksichtigt werden.
Habe den nachfolgenden Code eingeführt:
LaufNummer: (Select Count (*) FROM [Turnier] as Temp WHERE [Temp].[Summe Runden] > [Turnier].[Summe Runden])+1
Das führt zu dem im Anhang dargestellten Ergebnis. Ich möchte aber eine bei 1 beginnende steigende durchgehende Nummerierung.
Sorry, aber wir arbeiten uns ran ;)
Danke Michael
Du musst natürlich auch die übrigen Kriterien mit hinzunehmen:
WHERE [Temp].[Summe Runden] > [Turnier].[Summe Runden] AND
Turnier.Turniername=Temp.Turniername AND Turnier.Klasse_Grob_FS=Temp.Klasse_Grob_FS AND Turnier.Bogenklasse_FS=Temp.Bogenklasse_FS AND Turnier.Altersklasse_FS=Temp.Altersklasse_FS
Leider kann ich euch nicht umarmen. DANKE. Es funktioniert.
:) :-*