Anspringen eines Datensatzes innerhalb einer SQLite-Tabelle

Anfängerfragen zum Programmieren mit PureBasic.
Benutzeravatar
dysti
Beiträge: 656
Registriert: 10.02.2006 18:34
Wohnort: Schlicktown

Anspringen eines Datensatzes innerhalb einer SQLite-Tabelle

Beitrag von dysti »

Hallo,
ich möchte einen bestimmten Datensatz innerhalb einer SQLite-Tabelle anspringen, möchte aber die Blätterfunktion innerhalb der Tabeller behalten.
Aus dem untenstehenden Code kann man meine derzeitige Lösung ersehen.

Gibt es eine einfachere elegante Lösung, die ich bisher nicht gefunden habe?

Code: Alles auswählen

#db0=0
dbzaehler=0
UseSQLiteDatabase()
DatabaseFile$ = "i:\purebasic\forumexamples\bestand.sqlite"
;DatabaseFile$ = GetTemporaryDirectory()+"\Database.sqlite"
Debug DatabaseFile$
If CreateFile(#db0, DatabaseFile$)
   CloseFile(#db0)
   
   If OpenDatabase(#db0, DatabaseFile$, "", "")
      DatabaseUpdate(#db0, "CREATE TABLE bestand (Dsnr  INTEGER PRIMARY KEY AUTOINCREMENT UNIQUE  Not NULL, Name VARCHAR(40) , Stueck NUMERIC(10) , Preis NUMERIC(10,2))")
      DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('"+Name$+"', '"+Stueck$+"', '"+Str(Preis)+"')")
      DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('Tastatur', '5', '25.55')")
      DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('DVD-Laufwerk', '20', '33.00')")
      DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('Festplatte 160GB', '23', '133.00')")
      DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('USB-Stick 2GB', '44', '3.00')")
      If DatabaseQuery(#db0, "SELECT * FROM bestand")
         While NextDatabaseRow(#db0)
            Debug "Datensatznummer:  "+ GetDatabaseString(#db0, 0)
            Debug "Artikel        :  "+ GetDatabaseString(#db0, 1)
            Debug "Stück        :  "  + GetDatabaseString(#db0, 2)
            Debug "Preis          :  "+ GetDatabaseString(#db0, 3)
            dbzaehler=dbzaehler+1
         Wend
       EndIf
       
       ;letzten Datensatz ermitteln
       
       Result = DatabaseQuery(#db0, "SELECT max(Dsnr) from bestand");"SHOW TABLE STATUS FROM bestand LIKE 'Dsnr'")
         If Result = 0
         Debug DatabaseError()
         EndIf
         NextDatabaseRow(#db0)
         Debug "Dies ist die letzte Datensatznummer dieser Tabelle: "
         Debug GetDatabaseString(#db0, 0)
         Debug "oder so: " + Str(dbzaehler)
         
         
        ;zur Ausgangslage zurück
        DatabaseQuery(#db0, "SELECT * FROM bestand")
        
       
       
        ; wir wollen ein Datensatz anspringen, aber das blättern innerhalb der Tabelle soll erhalten bleiben
        ; in diesem Beispiel wollen wir den 3.Datensatz anspringen
            dbs=3 
            For i=1 To dbs
            NextDatabaseRow(#db0)
            Next
       
            Debug "_______________________"
            Debug ""
            Debug "Datensatznummer:  "+ GetDatabaseString(#db0, 0)
            Debug "Artikel        :  "+ GetDatabaseString(#db0, 1)
            Debug "Stück        :  "  + GetDatabaseString(#db0, 2)
            Debug "Preis          :  "+ GetDatabaseString(#db0, 3)
       
       FinishDatabaseQuery(#db0)
       
   Else
      Debug "Can't open database !"
   EndIf
Else
   Debug "Can't create the database file !"
EndIf 
PB5 / Spiderbasic / WB14 / Win7 / Win8.1 / Win10 / Debian 9
marco2007
Beiträge: 906
Registriert: 26.10.2006 13:19
Kontaktdaten:

Beitrag von marco2007 »

Ich weiß jetzt nicht was Du mit Blättern meinst, aber wenn ich ein bestimmte Zeile benötige, dann nehme ich einfach where...

Code: Alles auswählen

dbs=3
DatabaseQuery(#db0, "SELECT * FROM bestand where Dsnr="+Str(dbs))
FirstDatabaseRow(#db0)
  Debug "_______________________" 
  Debug "" 
  Debug "Datensatznummer:  "+ GetDatabaseString(#db0, 0) 
  Debug "Artikel        :  "+ GetDatabaseString(#db0, 1) 
  Debug "Stück        :  "  + GetDatabaseString(#db0, 2) 
  Debug "Preis          :  "+ GetDatabaseString(#db0, 3)  
Meinst Du das?
Windows 11 - PB 6.03 x64
_________________________________
Benutzeravatar
dysti
Beiträge: 656
Registriert: 10.02.2006 18:34
Wohnort: Schlicktown

Beitrag von dysti »

@marco2007,
das ist ansich normal richtig. Aber...
wenn du ab hier den nächsten Datensatz anspringen willst z.B. mit NextDatabaseRow(#db0), dann erleidest zu Schiffbruch.
Er hat dem dem Selectbefehl ja nur diesen Datensatz herausgefiltert
und somit erreiche ich Datensatz 5 nicht.
Ich könnte jetzt dbs=5 machen und die Query jedesmal wiederholen,
aber ich glaube nicht, das das professionell ist.
Jedesmal kommt durch den Befehl wieder Traffic auf, z. B. bei 20000 Datensätzen. Zumindest hat meine Festplatte ganz schön gerappelt.
Genau das soll verringert, wenn nicht sogar vermieden werden.
Bei 1000 Datensätzen merkt man nichts, da könnte man das vernachlässigen.
PB5 / Spiderbasic / WB14 / Win7 / Win8.1 / Win10 / Debian 9
Benutzeravatar
Kiffi
Beiträge: 10714
Registriert: 08.09.2004 08:21
Wohnort: Amphibios 9

Beitrag von Kiffi »

einfach nach Dsnr absteigend sortieren. Der erste Datensatz ist dann der
mit der höchsten Dsnr:

Code: Alles auswählen

#db0=0 
UseSQLiteDatabase() 
DatabaseFile$ = ":memory:" 
  
If OpenDatabase(#db0, DatabaseFile$, "", "") 

  DatabaseUpdate(#db0, "CREATE TABLE bestand (Dsnr  INTEGER PRIMARY KEY AUTOINCREMENT UNIQUE  Not NULL, Name VARCHAR(40) , Stueck NUMERIC(10) , Preis NUMERIC(10,2))") 
  DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('"+Name$+"', '"+Stueck$+"', '"+Str(Preis)+"')") 
  DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('Tastatur', '5', '25.55')") 
  DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('DVD-Laufwerk', '20', '33.00')") 
  DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('Festplatte 160GB', '23', '133.00')") 
  DatabaseUpdate(#db0, "INSERT INTO bestand (Name, Stueck, Preis) VALUES ('USB-Stick 2GB', '44', '3.00')") 
  
  If DatabaseQuery(#db0, "SELECT * FROM bestand Order By Dsnr Desc Limit 1") 
    
    While NextDatabaseRow(#db0) 
      Debug "Datensatznummer:  "+ GetDatabaseString(#db0, 0) 
      Debug "Artikel        :  "+ GetDatabaseString(#db0, 1) 
      Debug "Stück        :  "  + GetDatabaseString(#db0, 2) 
      Debug "Preis          :  "+ GetDatabaseString(#db0, 3) 
      Break
    Wend 
    
    FinishDatabaseQuery(#db0)
    
  EndIf 
  
Else 
  Debug "Can't open database !" 
EndIf
Grüße ... Kiffi

// Ups! Habe übersehen, dass Du einzelne DS direkt anspringen willst;
nicht den letzten (war noch im Gedanken in Deinem letzten Thread).
Zuletzt geändert von Kiffi am 31.07.2009 13:29, insgesamt 1-mal geändert.
a²+b²=mc²
marco2007
Beiträge: 906
Registriert: 26.10.2006 13:19
Kontaktdaten:

Beitrag von marco2007 »

Achso...
Wenn dsnr eine fortlaufende Nummer ist, könntest Du

Code: Alles auswählen

SELECT * FROM bestand where Dsnr>="+Str(dbs) +" order by Dsnr"
nehmen.
Windows 11 - PB 6.03 x64
_________________________________
Benutzeravatar
dysti
Beiträge: 656
Registriert: 10.02.2006 18:34
Wohnort: Schlicktown

Beitrag von dysti »

@marco2007,
und was ist, wenn der User sich überlegt, ich will nicht den nächsten sondern den vorherigen. Die Gedanken des Users kann man nicht vorhersehen.

Vielleicht sollte man sich überlegen, einen bestimmten Bereich der Tabelle
in einer Structure/Array/Linkedlist einzulesen.
Dann ist auch ein Listicongadget besser zu händeln, denn so eine große Datenbank kann man nicht in ein Listicongadget einlesen, oder bin ich auf ein Holzweg?
PB5 / Spiderbasic / WB14 / Win7 / Win8.1 / Win10 / Debian 9
marco2007
Beiträge: 906
Registriert: 26.10.2006 13:19
Kontaktdaten:

Beitrag von marco2007 »

ok, hätte ja sein können, dass Du die vorherigen nicht mehr brauchst.
Mach ich zum Beispiel -> Bei Vertriebsbelege lese ich nur Werte ab einem bestimmten Datum, da mich ältere nicht interessieren.

Repeat: Nextdatabaserow(): until Getdatabase...()=#true...sowas in der Art würde ich dann machen (anstatt for:next), obwohl ich mach`s eigentlich immer mit where...Wenn die Datenbank mal offen ist, sind die Abfragen eh immens schnell.
Windows 11 - PB 6.03 x64
_________________________________
Antworten