![]() |
Mehrere Suchbegriffe in einem Datensatz suchen
Ich möchte eine Suche durchführen. Das besondere daran(oder vielleicht auch nicht) ist, dass man drei Suchbegriffe eingeben kann. Also...er soll nachschauen, ob alle drei Suchbegriffe in einem Datensatz vorhanden ist. Ich habe folgenden Code von MrSpock erhalten:
Delphi-Quellcode:
SELECT * from personen
WHERE (abteilung = :abteilung) AND (reihe = :reihe) AND (nr = :nummer) Ich muss irgendwie mit den erzeugten Parametern auf ParamByName('abteilung').Value zugreifen. Vor dem Open muss ich dann alle 3 Parameter besetzen und schon bekommst ich nur die Sätze, die alle 3 Werte enthalten. Das ist das, welches ich nicht verstehe :freak: Vielen Dank nochmal an MrSpock :mrgreen: |
Hallo Flo,
da bin ich schon wieder :mrgreen: . Ziehe einmal eine TQuery Komponente auf das Formular und setze die Eigenschaft DatabaseName auf den Alias, den du auch für die Tabelle benutzt hast. Dann klicke die SQL Eigenschaft an und schreibe dort das oben gezeigte SQL Statement rein. Dabei musst du natürlich den Tabellennamen, der hinter from steht durch den echten Tabellennamen ersetzen (ohne die Endung .DB), außerdem musst du die drei Felder in der where Klausel durch die korrekten Namen der Felder der Tabelle ersetzen. Die 3 Bezeichner mit dem Doppelpunkt kannst du beliebig nennen, am besten natürlich so, dass die Bedeutung klar wird. Wenn dir das so weit nicht klar ist, dann poste einmal wie die Tabelle heißt und wie die 3 Felder, nach denen du suchen willst. |
Hallo,
ich hätte noch einen anderen Ansatz zu anzubieten, ohne der Parameterfunktion:
Delphi-Quellcode:
Damit kannst Du Variablen, Comboboxen, Edits usw. als "Parameter" für ein SQL-Statement Übergeben.
WITH Query1 DO
BEGIN Close; WITH SQL DO BEGIN Clear; Add('SELECT * '); Add('FROM Tabelle.db'); Add('WHERE Spalte1 = ' + CHR(39) + Edit1.Text + CHR(39)); Add('AND Spalte2 = ' + CHR(39) + LCB_AuftraegeFuer.Text + CHR(39)); // Lookupcombobox Add('AND TARGSTARTDATE <= ' + CHR(39) + DateToStr(DateTimePicker1.Date) + CHR(39)); END; Query1.Active := True; Open; END; END; |
Danke erst einmal für eure Antworten.
@MrSpock Soweit habe ich das hinbekommen. Aber ich weiß jetzt nicht, wie ich den Code per Buttonclick aufrufe. @APP Hab deinen Code auch mal ausprobiert, aber der klappt irgendwie nicht :cry: Hab ihn natürlich auch angepasst ! Hier ist er:
Delphi-Quellcode:
procedure TForm7.BitBtn1Click(Sender: TObject);
begin WITH Query1 DO BEGIN Close; WITH SQL DO BEGIN Clear; Add('SELECT * '); Add('FROM kosten.db'); Add('WHERE abteilung = ' + CHR(39) + Edit1.Text + CHR(39)); Add('AND reihe = ' + CHR(39) + edit2.Text + CHR(39)); // Lookupcombobox Add('AND Nr <= ' + CHR(39) + edit3.text + CHR(39)); END; Query1.Active := True; Open; END; end; |
Hallo Flo,
den abgebildeten Code fügst du in die Methode ein, die auf ein Doppelklick des OnClick Events des gewünschten Schalters erzeugt wird. Das "Open" der Query Komponente führt letztlich die Abfrage aus. Zum Code vom APP: Du solltest ihn wie folgt ändern:
Delphi-Quellcode:
WITH Query1 DO
BEGIN Close; WITH SQL DO BEGIN Clear; Add('SELECT * '); { Tabellenname ohne Punkt, sonst muss er in Anführungszeichen gestzt werden } Add('FROM kosten'); Add('WHERE abteilung = ' + CHR(39) + Edit1.Text + CHR(39)); { falls reihe und Nr Zahlenfelder sind, muss das Chr(39) weggelassen werden } Add('AND reihe = ' +edit2.Text); Add('AND Nr <= ' +edit3.text); END; Query1.Active := True; Open; END; |
Danke, aber ich bekomme folgende Fehlermeldung:
Ungültiges Schlüsselwort Symbol-String R1' and Nummer <= 1 Zeilennummer4 R1 ist die Reihe. Was sagt die Fehlermeldung aus und wie bekomme ich das Problem in den Griff? :roll: |
Hallo Flo,
wie gesagt, ob du Chr(39) um den Feldwert packen musst, hängt vom Datentyp ab. Ist "Reihe" ein Stringfeld, musst du Edit2.Text in "" übergeben, das gehtmit Chr(39)+Edit2.Text+Chr(39) oder einfacher über QuotedStr(Edit2.Text). Handelt es sich bei einem Feld um ein Numerisches Feld, muss der Wert von Editx.Text direkt benutzt werden. |
Jetzt kommt die Fehlermedlung:
'Keine Übereinstimmung der Typen im Ausdruck' :x |
Hallo Flo,
OK, dann poste doch bitte noch einmal die genaue Definition der Felder:
Mit dieser Info sollte es möglich sein, die Query klar und korrekt zu definieren. |
Ok....*such*....
in edit2 steht die abteilung, in edit2 steht die Reihe und in edit3 steht die Nummer. Abteilung = Abteilung, Reihe = Reihe, Nummer = Nummer. Abteilung und Nummer enthalten Zahlen und Buchstaben. Reihe nur Zahlen. Wenn noch was fehlt, bitte melden ! |
Hallo Flo,
also ich kenne mich nur mit Interbase und IBX aus und da geht folgendes immer.
Delphi-Quellcode:
Also einfach überall " und nich ' und bei Zahlen kann mann " schreiben oder auch nicht.
Add('SELECT * ');
Add('FROM kosten'); Add('WHERE abteilung = "' + Edit1.Text + '"'); Add('AND reihe = "' +edit2.Text+'"'); Add('AND Nr <= "' + edit3.text +'"'); Nochwas bei Interbase ist ein Select * immer langsamer als ein Select Feld1,Feld2,Feld3 ... Vieleicht hilft dir das ja weiter. :coder: |
Hallo Cobra,
ich denke, dass es so nicht ganz funktioniert. Ich hatte ja extra nach den Feldtypen gefragt. Nr ist ein numerisches Feld, sodass die Abfrage mit einem Zahlenwert und nicht mit einem String stattfinden muss:
Delphi-Quellcode:
Add('SELECT * ');
Add('FROM kosten'); Add('WHERE abteilung = "' + Edit1.Text + '"'); Add('AND reihe = "' +edit2.Text+'"'); Add('AND Nr <= ' + edit3.text); |
Also ich hab das jetzt nochmal probiert.
Jetzt sieht's so aus:
Delphi-Quellcode:
Da kommt aber wieder:
begin
WITH Query1 DO BEGIN Close; WITH SQL DO BEGIN Clear; Add('SELECT * '); Add('FROM kosten'); Add('WHERE abteilung = "' + Edit1.Text + '"'); Add('AND reihe = "' +edit2.Text+'"'); Add('AND nr <= ' + edit3.text); END; Query1.Active := True; Open; END;; end; Zitat:
|
Hallo MrSpock,
Interbase macht das mit aber jetzt wo ich es lese hat sich der Fehler ja auf die Datentypen bezogen. :thuimb: :hello: Dann bin ich jetzt auch dafür das deine Lösung die richtige ist. SQL ist eben nicht gleich SQL :wink: :coder: |
:wiejetzt: der Fehler kommt immernoch, dann gehen wir mal systematisch vor.
Mein erster Vorschlag wir fügen alles aufeinmal hinzu so können wir keine Leerzeichen vergessen. so also: Add('SELECT * FROM kosten.db WHERE abteilung = "' + Edit1.Text + '"' + ' AND reihe = "' +edit2.Text+'"' + ' AND nr <= ' + edit3.text); Mein zweiter Vorschalg es muß doch eine Testconsole geben für die SQL wo wir diese prüfen können und den Fehlerpunkt bestimmen kann. Machmal sind es kleine Fehler die eine große Wirkung haben. :coder: |
Also jetzt kommt ungültiges Schlüsselwort in Zeile 2 (select)
Code:
Delphi-Quellcode:
:roll: :roll: :roll:
WITH Query1 DO
BEGIN Close; WITH SQL DO BEGIN Clear; Add('SELECT * '); Add('SELECT * FROM kosten.db wHERE abteilung = "' + Edit1.Text + '"' + ' AND reihe = "' +edit2.Text+'"' + ' AND nummer <= ' + edit3.text); END; Query1.Active := True; Open; END;; |
!
Hallo Flo,
na diese Fehlermeldung ist einfach. Du hast ja "SELECT * SELECT * FROM ..." erzeugt, da ist das 2-te SELECT fehl am Platz. Also wenn die von dir angegebenen Feldtypen stimmen, dann versuch bitt mal folgendes:
Delphi-Quellcode:
Falls es nicht funktioniert, muss einer der Feldtypen nicht korrekt sein.
Add('SELECT * ');
Add('FROM kosten'); Add('WHERE abteilung = ' +QuotedStr(Edit1.Text)); Add('AND reihe =' +QuotedStr(edit2.Text)); Add('AND Nr <= ' + edit3.text); [edit=MrSpock]PS: In Edit3 muss eine gültige Ziffernfolge stehen![/edit] |
Vorweg: Es funktioniert immer noch nicht :cry:
Hab nochmals alles durchgeguckt, aber alles ist korrekt. Zitat:
In Edit2 soll die Reihe stehen..........Beispiel: R1 In Edit3 soll die Nummer stehen.........Beispiel: 1 Bin schon am Versweifeln :( |
Hallo Flo,
um ganz sicher zu gehen, habe ich den Originalcode wie folgt in ein kleines Programm gepackt:
Delphi-Quellcode:
Ich habe dazu eine Tabelle definiert, mit
procedure TForm1.Button2Click(Sender: TObject);
begin Query1.Close; with Query1.SQL do begin Clear; Add('SELECT * '); Add('FROM kosten'); Add('WHERE abteilung = ' +QuotedStr(Edit1.Text)); Add('AND reihe =' +QuotedStr(edit2.Text)); Add('AND Nr <= ' + edit3.text); end; Query1.Open; end; Abteilung A 20 Reihe A 20 Nr I ... und es funktioniert, wenn man in Edit1 z.B. A1, in Edit2 R1 und schließlich in Edit3 5 schreibt, ohne Fehler. Was für eine Datenbank nutzt du? Heißt das 3. Feld Nr oder Nummer? |
Hallo,
eine Anmerkung am Rande: Wenn ich mit umfangreichen Queries arbeiten muß, öffne ich einen (oder auch DEN) SQL-Explorer, mache einen Test-Alias oder benutze auch schon mal die vorhendenen Demo-Aliase und schreibe meine SQL-Statements in das SQL Fenster (natürlich angepasst und vereinfacht). (Man kann den SQL-Explorer z.B. über das Menü Datenbank/Explorer oder direkt beim TQuery1 auf dem Formular mit RechterMaus/Explorer im Kontextmenü öffnen) So habe ich immer den Überblick über die Feldnamen, Definitionen, usw..., wenn das Statement dann funktioniert übertrage ich es einfach in Delphi-Notation. |
Also...
@ MrSpock Ich hab den Code nachmal in mein Programm kopiert und überprüft. Funktioniert aber immer noch nicht. Zitat:
@ APP Hab alles nochmal im DB-Explorer kontrolliert. Es stimmt alles. |
Hallo Flo,
wenn dein Programm nicht zu groß ist, kann ich dir nur noch anbieten, das Programm (und die Tabellen) einmal dem nächsten Posting anzuhängen oder mir zu schicken, dann kann ich dort noch einmal reinschauen. |
Nur die Unit, in der der Fehler ist ???
|
Hallo Flo,
wenn diese Unit nicht auf andere Units zugreift (über die uses Klausel), dann genügt die Unit und die Tabellen. Benutzt du ein eigenes DataModule, dann solltest du das auch anhängen. |
Hallo Flo,
ich habe mir einmal deine Dateien angeschaut und den Fehler gefunden. Das dritte Feld "Nr" ist kein Zahlenfeld! Es ist definiert als A 5 (alphanumerisch 5 Zeichen lang). Es gibt jetzt 2 Möglichkeiten: Entweder du änderst den Typ des Feldes z.B. mit der Datenbankoberfläche in ein Integerfeld (I) oder zu änderst den Code in:
Delphi-Quellcode:
Bei der 2. Lösung musst du jedoch beachten, dass bei Vergleichen mit >= oder <= die Reihenfolge der Zeichen im ASCII Code entscheidend ist.
procedure TForm1.Button2Click(Sender: TObject);
begin Query1.Close; with Query1.SQL do begin Clear; Add('SELECT * '); Add('FROM kosten'); Add('WHERE abteilung = ' +QuotedStr(Edit1.Text)); Add('AND reihe =' +QuotedStr(edit2.Text)); Add('AND Nr <= ' + QuotedStr(edit3.text)); end; Query1.Open; end; |
Hab die erste Lösung genommen und es hat geklappt :spin:
Aber wieso springt er denn nicht zum Datensatz ? Muss ich da noch was hinzufügen ??? |
Hallo Flo,
in deinem Formular zeigst du ja den Inhalt der Tabelle an. Neben der Tabelle hast du jetzt eine Datenmenge mit einer Query (Abfrage) erstellt. Diese beiden Datenmengen haben aber nichts miteinander zu tun. Wenn du willst, dass die Tabelle auf den gewünschten Satz zeigt, kannst du mit Locate arbeiten (siehe OH) und die Query komplett vergessen.
Delphi-Quellcode:
procedure TForm1.Button1Click(Sender: TObject);
begin Table1.Locate('abteilung;reihe;grabstelle', VarArrayOf([Edit1.Text, Edit2.Text, Edit3.Text]),[]); end; |
Ohh....das tut mir jetzt leid :oops:
Hätte ich vielleicht vorher sagen bzw. schreiben sollen. Klappt aber. Vielen Dank nochmal an alle, die geholfen haben !!! |
Alle Zeitangaben in WEZ +1. Es ist jetzt 16:29 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz