Seltsames Datenbankverhalten

Für Themen zu Datenbanken und Zugriff auf diese. Auch für Datenbankkomponenten.

Seltsames Datenbankverhalten

Beitragvon Aliobaba » 15. Jan 2018, 18:23 Seltsames Datenbankverhalten

Hallo,

ich kämpfe schon zwei Tage mit einem eigenartigen Phänomen. Hier erstmal der Code:

Code: Alles auswählen
Procedure TForm2.Die_m_loeschen;
begin
    form1.ZConn1.ExecuteDirect('UPDATE tText SET Y1 = 0  ');
end;

Code: Alles auswählen
Procedure TForm2.Selektion_fixieren;
var
 mmm : string;
begin
  Form2.Die_m_loeschen// Habe dies im Laufe meiner Fehlersuche auch in eine extra Prozdur geschrieben, (nicht nötig)
  Form1.QText.First;
  while not Form1.QText.EOF do   
  begin                           
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m'// DB_Y1 ist ein Edit-Feld der Datenbank "TDBEdit"
     Form1.QText.Post;
     Form1.QText.Next;
  end;
end;         


Code: Alles auswählen
procedure TForm2.ausgabeClick(Sender: TObject);
begin
     Form2.Selektion_Zeigen (2)// 0:Sortierung nach Namen 1: nach Alter 2: nach Datum der Änderung
     Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount);
end;
Procedure TForm2.Selektion_Zeigen (aFlag : integer)// 0:Sortierung nach Namen 1: nach Alter 2: nach Datum der Änderung
var
   sss: string;
begin
     sss := 'Select * from tText WHERE Y1 = "m" ';
     if aFlag = 0 then sss := sss + 'ORDER BY UPPER(RTitel)' ;
     if aFlag = 1 then sss := sss + 'ORDER BY rDatumerstellt DESC' ;
     if aFlag = 2 then sss := sss + 'ORDER BY rDatumgeaendert DESC' ;
     Form1.QText.SQL.Clear;
     Form1.QText.SQL.Text := sss;
     Form1.QText.Open;
end;   


Ich habe das Ergebnis einer etwas komplizierteren Datenbankabfrage in einer Tabellenaufstellung (TDBGrid). Diese Selektion möchte ich aber später im Programm nochmal abrufen, wobei zu diesem späteren Zeitpunkt es aber nicht mehr so ohne weiteres möglich ist, diese Selektion nochmal zu generieren.

Deshalb folgendes Vorgehen. Es gibt in der benötigten Tabelle eine Spalte (column) "Y1". Zunächst schreibe ich in die gesamte Spalte "Y1" den Wert "0" rein. Dann gehe ich Schritt für Schritt die Tabellenaufstellung, die ich später nochmal aufrufen möchte, durch und schreibe in die Tabelle in die Spalte den Buchstaben "m" rein. Damit habe ich es später sehr leicht, meine exakte Selektion wieder aufzurufen.

Wenn ich nun schön der Reihe nach die obigen Prozeduren einzeln aufrufe, dann funktioniert alles prima.
Also:
1. Diese Procedur aufrufen: "Procedure TForm2.Selektion_fixieren;" Im SQLite-Studio sieht man sehr schön, dass überall da das "m" eingetragen wird, wo ich es hinhaben möchte.
2. Wenn ich nun beliebig später im Programm die Prozedur "procedure TForm2.ausgabeClick(Sender: TObject);" aufrufe, dann werden mir auch ganz wunderbar meine gewünschten Datenbankeinträge aufgelistet.

Seltsam ist nun folgendes: Wenn ich unmittelbar nach dem "'m'-Eintrag" in die Datenbank und innerhalb derselben Prozedur die Abfrage mache, dann funktioniert diese Abfrage nicht. Warum?

Also so:

Code: Alles auswählen
Procedure TForm2.Selektion_fixieren;
var
 mmm : string;
begin
  Form2.Die_m_loeschen;
  Form1.QText.First;
  while not Form1.QText.EOF do   
  begin                           
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m';
     Form1.QText.Post;
     Form1.QText.Next;
  end;
  Form2.Selektion_Zeigen ( 2 )// Hier also erfolgt der sofortige Aufruf, der oben per separater Prozedur erfolgt.
  Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount);
end;     


Danke schonmal!
Aliobaba

Die verwendete Datenbank ist SQLite.
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Aliobaba » 16. Jan 2018, 00:44 Re: Seltsames Datenbankverhalten

Hallo und einen Guten Morgen,

Sorry, wenn ich mich nochmal melde; Zwischenzeitlich (es ist 01:40 Uhr) konnte ich mein Problem nochmal ein wenig eingrenzen:

Offenbar führt das Beschreiben der Felder in der Spalte "Y1-4" mit einem Zeichen (hier "0") dazu, dass die Selektion in der DBGrid-Spalte nicht mehr richtig durchlaufen wird.
Wenn ich die Zeile1 (sh Code) irgendwo im Programm etwas früher abarbeiten lasse, dann wird der "Text: "m"" korrekt in die Datenbank geschrieben.
Wenn diese Zeile1 aber unmittelbar vorher in derselben Prozedur steht, dann erfolgt dieser Eintrag ("m") nicht.

Woran kann das liegen?

Aliobaba

Code: Alles auswählen
  form1.ZConn1.ExecuteDirect('UPDATE tText SET Y1 = 0 , Y2 = 0 , Y3 = 0 , Y4 = 0 ')// hier genannt: Zeile1
 
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m'// DB_Y1 ist ein Edit-Feld der Datenbank "TDBEdit" Spalte "Y1"
     Form1.QText.Post;
     Form1.QText.Next;
  end;
 
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon af0815 » 16. Jan 2018, 06:44 Re: Seltsames Datenbankverhalten

Füge das Statement aus dem ExecuteDirect der Connection in eine normale Query und führe die Query direkt aus. Nicht das du das Buffermanagement der Komponenten beeinflusst durch den Wechsel zwischen Komponente und Direktzugriff über die Connection.

Andreas
Blöd kann man ruhig sein, nur zu Helfen muss man sich wissen (oder nachsehen in LazInfos/LazSnippets).
af0815
 
Beiträge: 3322
Registriert: 7. Jan 2007, 10:20
Wohnort: Niederösterreich
OS, Lazarus, FPC: Win7/Linux (L stable FPC stable) per fpcup | 
CPU-Target: 32Bit (64Bit)
Nach oben

Beitragvon Aliobaba » 16. Jan 2018, 08:35 Re: Seltsames Datenbankverhalten

af0815 hat geschrieben:Füge das Statement aus dem ExecuteDirect der Connection in eine normale Query ...

Danke, Andreas für die schnelle Antwort,

kannst Du mir dabei helfen wie Du das meinst?
Das geht aber doch nur in einer anderen Query als "QText" - also eine neue Query, z.B. "QText_xy" ?
Und wie fügt man dieses "ExecuteDirect" in eine Query ein?

Aliobaba

af0815 hat geschrieben:Nicht das du das Buffermanagement der Komponenten beeinflusst durch den Wechsel zwischen Komponente und Direktzugriff über die Connection.
So könnte ich mir das Entstehen dieses Fehlers auch vorstellen, Danke!
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Soner » 16. Jan 2018, 13:30 Re: Seltsames Datenbankverhalten

Hier stimmt irgendwas ganz nicht. In dieser Reihenfolge machst du das:
1) Irgendwo selektierst du tText (Selektion_Zeigen) und zwar mit ' WHERE Y1 = "m" '
2) Danach setzt du tText.Y1=0
3) Und jetzt versuchst du mit der gleichen Query aus Punkt 1) tText.Y1=m zu setzen.
Das wird nie klappen, weil für die Abfrage aus Punkt 1. ist tText.Y1=m.
Es weiß nicht von der Aktion das du in Punkt 2) gemacht hast.
Damit es von der Änderungen mitbekommt muß du schließen und neu öffnen etwa so:
Code: Alles auswählen
 
Procedure TForm2.Selektion_fixieren;
var
 mmm : string;
begin
  Form2.Die_m_loeschen// Habe dies im Laufe meiner Fehlersuche auch in eine extra Prozdur geschrieben, (nicht nötig)
 
 //hier XXXXXXXXXXXXXXXXXXXX
 Form1.QText.Close;
 Form1.QText.Open;
 
  Form1.QText.First;
  while not Form1.QText.EOF do   
  begin                           
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m'// DB_Y1 ist ein Edit-Feld der Datenbank "TDBEdit"
     Form1.QText.Post;
     Form1.QText.Next;
  end;
end;   
 
Soner
 
Beiträge: 398
Registriert: 26. Sep 2012, 23:07
Wohnort: Hamburg
OS, Lazarus, FPC: Win7Pro-32Bit, Immer letzte Lazarus Release mit SVN-Fixes | 
CPU-Target: 32Bit
Nach oben

Beitragvon Aliobaba » 16. Jan 2018, 17:16 Re: Seltsames Datenbankverhalten

Danke, Soner,

dann habe ich mich missverständlich ausgedrückt, bitte entschuldige:

Als erstes setze ich Y1 auf 0, und zwar die gesamte Column, also alle Einträge in Y1
Dann selektiere ich die Texte in einer Abfrage (die aber nicht beliebig im Programm reproduzierbar ist)
Bei den selektierten Texten setze dann ich Y1 auf m
Und dann kann ich (in aller Ruhe) eine SQL-Abfrage nach diesem "m" machen.

Das funktioniert hervorragend, wenn ich dieses "0-Setzen" vorab irgendwo im Programm mache.
Es funktioniert aber nicht, wenn ich dies unmittelbar vor dem Schritt mache, mit dem ich bei den selektierten Texten das Y1 auf "m" setze.

Ich halte die Erklärung von "af0815" für recht einleuchtend. Es könnte am "Buffermanagement" liegen (was immer das ist). Es sieht wirklich so aus, dass - wenn ich die beschriebenen Schritte unmittelbar hintereinander mache - beim Durchlauf der selektierten Texte der 0-Eintrag irgendwie noch nicht im TDBEdit-Feld "vorliegt".

Wie gesagt, es funktioniert ja prima, wenn ich das 0-Setzen deutlicher vor dem m-setzen mache. Damit kann ich gut leben; mich interessiert halt ganz einfach, warum dieses Verhalten so ist und wie man handeln müsste, wenn es programmtechnisch nicht möglich wäre, dieses 0-Setzen bereits "im Vorfeld" zu machen.

Außerdem ginge Dein Vorschlag auch nicht, da man nach dem Schließen und wieder Öffnen der Datenbank die Query nochmal machen müsste. Und das geht kaum, da sich die Programmsituation zwischenzeitlich so geändert hat, dass man nicht mehr auf dasselbe Query-Ergebnis kommt.

Danke!
Aliobaba
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Soner » 16. Jan 2018, 22:16 Re: Seltsames Datenbankverhalten

Eigentlicht meint af0815 mit "Buffermanagement" dasselbe, diese Aussage stimmt laut deinem Code nicht:
Aliobaba hat geschrieben:Danke, Soner,

dann habe ich mich missverständlich ausgedrückt, bitte entschuldige:

Als erstes setze ich Y1 auf 0, und zwar die gesamte Column, also alle Einträge in Y1
Dann selektiere ich die Texte in einer Abfrage (die aber nicht beliebig im Programm reproduzierbar ist)
Bei den selektierten Texten setze dann ich Y1 auf m
Und dann kann ich (in aller Ruhe) eine SQL-Abfrage nach diesem "m" machen.
..


Schau her, lies meine Kommentare:
Code: Alles auswählen
 
Procedure TForm2.Selektion_fixieren;
var
 mmm : string;
begin
  //Form1.QText ist schon irgendwo schon gestartet, also die Ergebnisse liegen im DB-Buffer
 
  //hier machst du tText SET Y1 = 0
  Form2.Die_m_loeschen;
 
 //Form1.QText ist noch aktiv und es weiß nicht von Löschaktion von eine Zeile drüber
 //und du setzt gleich vom alten Auswahl  Form1.DB_Y1.Text:='m';
 //da aber hier laut dein Auswahl Form1.DB_Y1.Text immer gleich 'm' war
 //denkt ZQuery es wurde nichts geändert macht wahrscheinlich keine updates.
 //deshalb mußt du hier referesh machen, am einfachsten einmal die Query schließen und anschließend öffnen
 
  Form1.QText.First;
  while not Form1.QText.EOF do   
  begin                           
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m';
     Form1.QText.Post;
     Form1.QText.Next;
  end;
  Form2.Selektion_Zeigen ( 2 ) ;
  Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount);
end;   
 



Aliobaba hat geschrieben:...
Außerdem ginge Dein Vorschlag auch nicht, da man nach dem Schließen und wieder Öffnen der Datenbank die Query nochmal machen müsste. Und das geht kaum, da sich die Programmsituation zwischenzeitlich so geändert hat, dass man nicht mehr auf dasselbe Query-Ergebnis kommt.
..


Ich habe ja nicht gesagt Datenbank (TZConnection) schließen, sondern Auswahl(Form1.QText) refresh machen mit schließen und öffnen.
Wenn du das in DisableControls/Enablecontrols packst, bekommt der Benutzer nichtmal davon.
Und noch eins, man muß nicht jedesmal Sql neu setzen. Du kannst mit TZQuery.Close Auswahl schließen und nachher mit TZQuery.Open öffnen SQL-String geht nicht verloren.

Kennst du das, das ist ziemlich nützlich wenn man viel mit Datenbanken arbeitet.
Code: Alles auswählen
 
var AktuellePosition : TBookMark;
begin
 try
  AktuellePosition:=ZQuery1.Bookmark; //merken
 
  ZQuery1.DisableControls;   // TDBGrid und Andre DB-Controls sollen jezt nicht aktiviert werden
 
  //jetzt irgendetwas mit query machen z.b.
  ZQuery1.First;
  while not ZQuery1.EOF do begin
    //...
   ZQuery1.Next;
  end;
 
  // Position zurücksetzen, der Benutzer merkt dann nicht dass es gescrollt wurde
  // am besten im try-except weil falls was gelöscht kann Fehler auftreten, so passiert dann nichts.
   try
     ZQuery1.Bookmark:=AktuellePosition;
   except
     on E: Exception do ; //nichts machen
   end;
 
 finally
  ZQuery1.EnableControls;   // TDBGrid und Andre DB-Controls sollen jezt aktiviert werden
 end;
 
end;
 


Edit:

Du sagst ja ganz oben:
Aliobaba hat geschrieben:...

Wenn ich nun schön der Reihe nach die obigen Prozeduren einzeln aufrufe, dann funktioniert alles prima.
Also:
1. Diese Procedur aufrufen: "Procedure TForm2.Selektion_fixieren;" Im SQLite-Studio sieht man sehr schön, dass überall da das "m" eingetragen wird, wo ich es hinhaben möchte.
2. Wenn ich nun beliebig später im Programm die Prozedur "procedure TForm2.ausgabeClick(Sender: TObject);" aufrufe, dann werden mir auch ganz wunderbar meine gewünschten Datenbankeinträge aufgelistet.

...

Genau das machst du hier was ich meine. Erst bearbeiten (0 setzen), dann in procedure TForm2.ausgabeClick(Sender: TObject); neu laden (refresh).
Soner
 
Beiträge: 398
Registriert: 26. Sep 2012, 23:07
Wohnort: Hamburg
OS, Lazarus, FPC: Win7Pro-32Bit, Immer letzte Lazarus Release mit SVN-Fixes | 
CPU-Target: 32Bit
Nach oben

Beitragvon Aliobaba » 17. Jan 2018, 00:10 Re: Seltsames Datenbankverhalten

Vielen Dank für Deine Hilfe!

sh. bitte meine Kommentare
Code: Alles auswählen
Procedure TForm2.Selektion_sortieren_nach_Kriterien (aFlag : integer)// 0:Sortierung nach Namrn 1: nach Alter 2: nach Datum der Änderung
begin
                   // Das Abfrageergebnis einer Query liegt in einer TDBGrid vor
                   // Nun wird die Column Y1 vollständig auf "0" gesetzt
  form1.ZConn1.ExecuteDirect('UPDATE tText SET Y1 = 0  ');
                   // Jetzt wird NUR für die Datensätze in der TDBGrid das Feld auf "m" gesetzt
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin
     Form1.QText.Edit;
     Form1.DB_Y1.Text:='m'// DB_Y1 ist ein Edit-Feld der Datenbank "TDBEdit" Spalte "Y1"
     Form1.QText.Post;
     Form1.QText.Next;
  end;
  Form1.QText.Close;                                                    // Dein Vorschlag ? habe ich das richtig verstanden?
  Form1.QText.Open;                                                     // Dein Vorschlag ? habe ich das richtig verstanden? 
                  // Und jetzt wird der Datenbestand selektiert bzgl des Feldes Y1=m
  Form2.Selektion_Zeigen ( aFlag )// 0:Sortierung nach Namen 1: nach Alter 2: nach datum der Änderung
end;           
 
Procedure TForm2.Selektion_Zeigen (aFlag : integer)// 0:Sortierung nach Namen 1: nach Alter 2: nach datum der Änderung
var
   sss: string;
begin
     sss := 'Select * from tText WHERE Y1 = "m" ';
     if aFlag = 0 then sss := sss + 'ORDER BY UPPER(RTitel)' ;
     if aFlag = 1 then sss := sss + 'ORDER BY rDatumerstellt DESC' ;
     if aFlag = 2 then sss := sss + 'ORDER BY rDatumgeaendert DESC' ;
 
     Form1.QText.SQL.Clear;
     Form1.QText.SQL.Text := sss;
     Form1.QText.Open;
end;       


Das funktioniert! Jetzt passiert aber wieder etwas völlig Unerwartetes!!
Wenn ich diese Prozedur unmittelbar hintereinander mit einem "neuen Mausklick" auf einen entsprechenden Button ein zweites mal aufrufe, dann werden ALLE Datensätze angezeigt, obwohl in der TDBGrid die korrekt selektierten Datensätze angezeigt werden!? :|
Alles läuft korrekt, wenn dieses "UPDATE tText SET Y1 = 0 " schon vorher irgendwo im Programm gemacht habe. :cry:

Aliobaba
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Aliobaba » 17. Jan 2018, 00:14 Re: Seltsames Datenbankverhalten

... tolle Sache, das mit dem "Bookmark" :) ... was es so alles gibt!
Danke!
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Soner » 17. Jan 2018, 02:06 Re: Seltsames Datenbankverhalten

close/open sollte vor Form1.QText.First; stehen, aber weist du was mir auffällt, du selektierst in Selektion_Zeigen Datensätze mit "WHERE Y1 = "m" " nur jetzt mit close/open geht der Auswahl verloren.
Ich kann ohne ganze Zusammenspiel der Db-TAbellen und Query nicht viel sagen, sorry.

Mach das hier (Ich habe deine Kommentare gelöscht damit du meine Kommentare sehen kannst):
Code: Alles auswählen
 
Procedure TForm2.Selektion_sortieren_nach_Kriterien (aFlag : integer) ;
begin
  //du hast irgendwo  nach irgendwelche Kriterien Form1.QText ausgewählt, das ist uns unbekannt
 
 
  form1.ZConn1.ExecuteDirect('UPDATE tText SET Y1 = 0  ');
 
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin
     //mach doch direkt weil du  Form1.QText gleicht neu öffnest in  Form2.Selektion_Zeigen
     form1.ZConn1.ExecuteDirect('UPDATE tText SET Y1 = "m" WHERE  tTextID= '+Form1.QText.FieldbyName('tTextID').AsString);
     // tTextID ist der Name von Indexspalte der tText-Tabelle. Ich denke mal du hast so etwas in deiner TAbelle
 
     //Form1.QText.Edit;
     //Form1.DB_Y1.Text:='m';
     //Form1.QText.Post;
 
     Form1.QText.Next;
  end;
 
 
  Form2.Selektion_Zeigen ( aFlag ) ;
end;
 
Soner
 
Beiträge: 398
Registriert: 26. Sep 2012, 23:07
Wohnort: Hamburg
OS, Lazarus, FPC: Win7Pro-32Bit, Immer letzte Lazarus Release mit SVN-Fixes | 
CPU-Target: 32Bit
Nach oben

Beitragvon Aliobaba » 17. Jan 2018, 07:32 Re: Seltsames Datenbankverhalten

Moin, Soner,

Whow! 2:06 Uhr!
Bin heute den ganzen Tag nicht zu Hause und probiere Deine Vorschläge noch aus und melde mich auf jeden Fall wieder.
Hab auch noch eine deutlich elegantere Lösung im Kopf....
Trotzdem ist es seltsam, dass bei einem unmittelbar wiederholten Aufruf der Prozedur bei identischem Query-Ergebnis als Ausgangssituation ein unterschiedliches Ergebnis rauskommt :?: 8)

Einen schönen Tag noch!
Aliobaba
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Soner » 17. Jan 2018, 16:57 Re: Seltsames Datenbankverhalten

Aliobaba hat geschrieben:Moin, Soner,

Whow! 2:06 Uhr!
Bin heute den ganzen Tag nicht zu Hause und probiere Deine Vorschläge noch aus und melde mich auf jeden Fall wieder.
Hab auch noch eine deutlich elegantere Lösung im Kopf....
Trotzdem ist es seltsam, dass bei einem unmittelbar wiederholten Aufruf der Prozedur bei identischem Query-Ergebnis als Ausgangssituation ein unterschiedliches Ergebnis rauskommt :?: 8)

Einen schönen Tag noch!
Aliobaba


Momentan bin ich schwer erkältet, schlafe den ganzen Tag, wenn mitten in der Tag aufwache, muss ich Zeit schinden damit ich weiterschlafen kann :D
Soner
 
Beiträge: 398
Registriert: 26. Sep 2012, 23:07
Wohnort: Hamburg
OS, Lazarus, FPC: Win7Pro-32Bit, Immer letzte Lazarus Release mit SVN-Fixes | 
CPU-Target: 32Bit
Nach oben

Beitragvon Aliobaba » 17. Jan 2018, 17:53 Re: Seltsames Datenbankverhalten

Hallo Soner,

und werde bitte schnell wieder gesund! Hoffentlich geht es Dir schon besser!

Ich habe Deine Anregungen umgesetzt; funktioniert mit ein paar kleinen Änderungen gut.
Trotzdem ist nun auch meine neue Idee verwirklich - und die ist deutlich schneller:

Schau mal bitte (wenn es Dir wieder besser geht). Meine Anmerkungen wieder in den Kommentaren:


Code: Alles auswählen
Procedure TForm2.Selektion_sortieren_nach_Kriterien (aFlag : integer)// 0:Sortierung nach Namrn 1: nach Alter 2: nach datum der Änderung
begin
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ')// X5 entspricht dem Y1 von früher
  Form1.QText_ID_initialisieren; // Eine andere(!!) Query, die alle vorhandenen Datensätze enthält
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin     
   //  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = "5" WHERE  tTextID= ' + Form1.QText.FieldbyName('rID').AsString);
   //  hab's nur ein wenig umgeschrieben,da im ExecuteDirect Befehl keine Variablen stehen können (Weiß aber, was du meinst)
     Form1.QText.Edit;
     With form1.QText_ID do     // Qtext_ID  "_ID"!  // Das ist die andere Query, die ALLE Datenbankeinträge enthält (sonst geht es nicht)
     Begin
       SQL.Clear;
       SQL.Text := 'UPDATE tText SET X5 = "5" ';
       SQL.Add(' WHERE rID =:TxID');
       ParamByName('TxID').AsString :=  Form1.QText.FieldbyName('rID').AsString;
       ExecSQL;
    end;
    Form1.QText.Next;
  end;
  Form2.Selektion_Zeigen ( aFlag )// 0:Sortierung nach Namen 1: nach Alter 2: nach datum der Änderung
  Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount); //ab jetzt nur noch kleine programminterne Routinen
  Form2.GridTitel_Focus_geben;
  Form2.Check_gezeigten_Datensatz (1);
end;   


Code: Alles auswählen
Procedure TForm2.Selektion_Zeigen (aFlag : integer)// 0:Sortierung nach Namen 1: nach Alter 2: nach datum der Änderung
var
   sss: string;
begin
     sss := 'Select * from tText WHERE X5 = "5" ';
     if aFlag = 0 then sss := sss + 'ORDER BY UPPER(RTitel)' ;
     if aFlag = 1 then sss := sss + 'ORDER BY rDatumerstellt DESC' ;
     if aFlag = 2 then sss := sss + 'ORDER BY rDatumgeaendert DESC' ;
 
     Form1.QText.SQL.Clear;
     Form1.QText.SQL.Text := sss;
     Form1.QText.Open;
end

Mit obiger Prozedur funktioniert es sehr gut!

Hier nun mein "neues Werk" ; funktioniert viel schneller, da viel weniger Datenbankabfragen
Sehr vieles ist in der "Where"-Abfrage drinnen : 150 mal "or"!

Code: Alles auswählen
Procedure TForm2.Selektion_sortieren_nach_Kriterien_2 (aFlag : integer)// 0:Sortierung nach Namrn 1: nach Alter 2: nach Datum der Änderung
var
 nn : integer;
 AWhere : String;
begin
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  Form1.QText_ID_initialisieren; // Eine andere Query, die nun alle vorhandenen Datensätze enthält
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  nn := 0;
  AWhere := 'Where rID = "9"';     // IDVariable erzeugen  "9" wird (absichtlich) nie gefunden
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin
     nn := nn + 1 ;
     AWhere := AWhere + ' OR rID=' + Form1.QText.FieldbyName('rID').AsString;
          if ( nn = 150) or ( nn = Form1.QText.RecordCount )  then
          begin
             With form1.QText_ID do     // Qtext_ID  "_ID"!
             Begin
               SQL.Clear;
               SQL.Text := 'UPDATE tText SET X5 = "5" ' + AWhere ;
               ExecSQL;
            end;
            nn := 0;
            AWhere := 'Where rID = "9"';             // IDVariable erzeugen
          end;
  Form1.QText.Next;
  end;
  Form2.Selektion_Zeigen ( aFlag )// 0:Sortierung nach Namen 1: nach Alter 2: nach Datum der Änderung
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount);
  Form2.GridTitel_Focus_geben;
  Form2.Check_gezeigten_Datensatz (1);
end;   
 
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Aliobaba » 17. Jan 2018, 19:03 Re: Seltsames Datenbankverhalten

.... sorry! So stimmt's: :oops:

Code: Alles auswählen
Procedure TForm2.Selektion_sortieren_nach_Kriterien_2 (aFlag : integer)// 0:Sortierung nach Namrn 1: nach Alter 2: nach Datum der Änderung
var
 nn , mm : integer;  //!!  "mm" braucht man noch!
 AWhere : String;
begin
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  Form1.QText_ID_initialisieren; // Eine andere Query, die nun alle vorhandenen Datensätze enthält
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  mm := 0//!!
  nn := 0;
  AWhere := 'Where rID = "9"';     // IDVariable erzeugen  "9" wird (absichtlich) nie gefunden
  Form1.QText.First;
  while not Form1.QText.EOF do     // Die Text-ID's werden der Reihe nach aufgerufen
  begin
     nn := nn + 1 ;
     mm := mm + 1//!!
     AWhere := AWhere + ' OR rID=' + Form1.QText.FieldbyName('rID').AsString;
          if ( nn = 150) or ( mm = Form1.QText.RecordCount )  then    //!!
          begin
             With form1.QText_ID do     // Qtext_ID  "_ID"!
             Begin
               SQL.Clear;
               SQL.Text := 'UPDATE tText SET X5 = "5" ' + AWhere ;
               ExecSQL;
            end;
            nn := 0;
            AWhere := 'Where rID = "9"';             // IDVariable erzeugen
          end;
  Form1.QText.Next;
  end;
  Form2.Selektion_Zeigen ( aFlag )// 0:Sortierung nach Namen 1: nach Alter 2: nach Datum der Änderung
  form1.ZConn1.ExecuteDirect('UPDATE tText SET X5 = 0  ');
  Form2.Lb_Anzahl_DS_gezeigt.Caption := IntToStr(Form1.QText.RecordCount);
  Form2.GridTitel_Focus_geben;
  Form2.Check_gezeigten_Datensatz (1);
end;   
Mein Lazarus-Lieblingsprojekt: "MyMemoryDB" ( http://www.mymemorydb.n-bay.de/ )
Aliobaba
 
Beiträge: 317
Registriert: 1. Mai 2012, 08:11

Beitragvon Soner » 18. Jan 2018, 00:59 Re: Seltsames Datenbankverhalten

So jetzt bin ich wieder aufgewacht :D
Wenn du das Problem gelöst hast, dann ist es gut.

Was mir auffält ist, du arbeitest in der Prozedur Selektion_sortieren_nach_Kriterien_2 die Query Form1.QText Zeile für Zeile ab. Hat die SQL-Anweisung eine Where-Teil?
Wenn es hat, dann würde ich diesen Where-Teil in einer String-Variable zwischenspeichern und verwenden, dann ginge es einfacher, etwa so:
Code: Alles auswählen
 
  form1.QText_ID.SQL.Text := 'UPDATE tText SET X5 = "5" WHERE ' + Where_Teil_Von_Form1_QText;
  form1.QText_ID.ExecSQL;
 

Dann sparts du, den Loop.
Soner
 
Beiträge: 398
Registriert: 26. Sep 2012, 23:07
Wohnort: Hamburg
OS, Lazarus, FPC: Win7Pro-32Bit, Immer letzte Lazarus Release mit SVN-Fixes | 
CPU-Target: 32Bit
Nach oben

» Weitere Beiträge siehe nächste Seite »
Nächste

Zurück zu Datenbanken



Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 1 Gast

porpoises-institution
accuracy-worried