AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Programmierung allgemein Programmieren allgemein SQL: benachbarte Datensätze mitselektieren
Thema durchsuchen
Ansicht
Themen-Optionen

SQL: benachbarte Datensätze mitselektieren

Ein Thema von Hedge · begonnen am 3. Jul 2009 · letzter Beitrag vom 4. Jul 2009
Antwort Antwort
Seite 1 von 3  1 23      
Hedge

Registriert seit: 30. Jun 2007
278 Beiträge
 
Delphi 2009 Professional
 
#1

SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 20:32
Folgendes Problem.
Meine Datensätze werden geordnet.
Für einen bestimmten Datensatz ist der Primary-Key bekannt.

Aus der Tabelle möchte ich dieses Element inklusive der 2 nächstkleineren Elemente und der 2 nächstgrößeren Elemente als Ergebnismenge verarbeiten.

Hat Jemand eine Idee wie ich das mit weniger als 3 Queries schaffen kann?
٩๏̯͡๏)۶
  Mit Zitat antworten Zitat
Benutzerbild von alcaeus
alcaeus

Registriert seit: 11. Aug 2003
Ort: München
6.537 Beiträge
 
#2

Re: SQL: Nachbarn eines Datensatzes mitselektien

  Alt 3. Jul 2009, 20:42
Moin,

es ist eigentlich simpel: nehmen wir an, du sortierst nach dem Feld id. Dir ist die ID des eigentlichen Datensatzes bekannt, d.h. du selektierst erstmal das Objekt:
SELECT * FROM foo WHERE id = %id Anschliessend selektierst du die naechsten 2 Datensaetze:
SELECT * FROM foo WHERE id > %id ORDER BY id ASC LIMIT 2 Und zu guter Letzt noch die vorherigen beiden:
SELECT * FROM foo WHERE id < %id ORDER BY id DESC LIMIT 2 So, das waren jetzt drei. Wir koennen die ersten beiden Queries aber verbinden:
SELECT * FROM foo WHERE id >= %id ORDER BY id ASC LIMIT 3 Nun weisst du dass die erste Row des Ergebnis-Sets der eigentliche Datensatz ist und alles was nachher kommt sind die naechsten Datensaetze, und hast das Ganze in 2 Queries. Auf ein Query runterzukommen geht eigentlich nur mit Hilfe von UNION:
SQL-Code:
(SELECT * FROM foo WHERE id < %id ORDER BY id DESC LIMIT 2)
UNION (SELECT * FROM foo WHERE id >= %id ORDER BY id ASC LIMIT 3)
ORDER BY id ASC
Hab ich grad nicht getestet, muesste aber funktionieren. Das Ding ist allerdings ein Trugschluss, da der DB-Server intern sowieso 2 Queries ausfuehrt, von daher kannst du es uebersichtlicher halten, wenn du getrennt selektierst.

Lustiger wird das Ganze wenn du nicht ein Sortierkriterium hast, sondern mehrere. Nehmen wir an du hast einen Vornamen (firstname) und einen Nachnamen (lastname) und moechtest nach der Form lastname, firstname sortieren und selektieren. In dem Fall musst du die Sortierung selbst basteln:

SELECT * FROM foo WHERE lastname > %lastname OR (lastname = %lastname AND firstname > %firstname) ORDER BY lastname ASC, firstname ASC LIMIT 2 SELECT * FROM foo WHERE lastname < %lastname OR (lastname = %lastname AND firstname < %firstname) ORDER BY lastname DESC, firstname DESC LIMIT 2 Du kannst dir vorstellen, wie sich das Ding aufblaeht, wenn du dann 5 Kriterien drin hast
In diesem Fall ist es uebrigens fast immer geschickter, mit 3 Queries zu arbeiten. Schliesslich wird dein Datensatz wohl kaum per Vor- und Nachname definiert werden, sondern per ID. Also musst du dir erstmal die Grenzen aus der Datenbank holen, was in diesem Fall nicht mit einem Subquery oder JOIN gemacht werden sollte, da du ihn gleich zwei Mal machen musst (einmal fuer die vorherigen 2 Datensaetze, einmal fuer die nachfolgenden). Dein DB-Server wirds dir spaetestens ab 4-stelligen Datensatzzahlen danken *g*

Greetz
alcaeus
Andreas B.
Die Mutter der Dummen ist immer schwanger.
Ein Portal für Informatik-Studenten: www.infler.de
  Mit Zitat antworten Zitat
Hedge

Registriert seit: 30. Jun 2007
278 Beiträge
 
Delphi 2009 Professional
 
#3

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 20:46
Wow super.
Immerhin nur 2 Abfragen

Könnte man das Ganze mit Stored Procedures verbessern?

EDIT: Mein Fall ist noch ein wenig schwieriger.
Mir ist die ID des Users geläufig nach der ich selektieren kann, aber nicht wie groß das Sortierkriterium des Users ist.
Also sind es dann doch 3 Abfragen :/
٩๏̯͡๏)۶
  Mit Zitat antworten Zitat
Benutzerbild von alcaeus
alcaeus

Registriert seit: 11. Aug 2003
Ort: München
6.537 Beiträge
 
#4

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 21:02
Zitat von Hedge:
Mir ist die ID des Users geläufig nach der ich selektieren kann, aber nicht wie groß das Sortierkriterium des Users ist.
Du meinst also den letzten Fall, den ich beschrieben hab? Ja, in dem Fall musst du es leider mit dreien machen, es sei denn du willst mit Subqueries arbeiten:

SQL-Code:
SELECT * FROM foo a
WHERE a.sort >= (SELECT sort FROM foo b WHERE id = %id)
ORDER BY sort ASC
LIMIT 3
Das ist aber wieder nur Augenauswischerei, denn der DB-Server wird definitiv drei Queries machen. Du koenntest es ueber nen JOIN loesen, aber dann wirds ab ner gewissen Datensatzmenge einfach haesslich.

Greetz
alcaeus

Edith sagt: SPs? Keine Ahnung...als eingefleischter MySQL-User komm ich erst seit Kurzem in den Genuss solcher Features und hatte noch nicht die Zeit, mich damit zu befassen
Andreas B.
Die Mutter der Dummen ist immer schwanger.
Ein Portal für Informatik-Studenten: www.infler.de
  Mit Zitat antworten Zitat
Hansa

Registriert seit: 9. Jun 2002
Ort: Saarland
7.554 Beiträge
 
Delphi 8 Professional
 
#5

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 21:18
SQL-Code:
for select first 3 M.ID, M.ABDATUM, M.MWSTWERT from MWST8 M
    where M.MWSTSATZ = :MWSTSATZ_OUT and M.ABDATUM <= :ABDATUM
    order by M.ABDATUM desc
    INTO :ID_OUT,:ABDATUM_OUT,:MWSTWERT_OUT DO
      SUSPEND;
    END
END
^
So ungefähr geht das mit SP unter Firebird. DB wurde nicht angegeben. First heißt woanders eventuell auch Limit oder sonstwie.
Gruß
Hansa
  Mit Zitat antworten Zitat
Hedge

Registriert seit: 30. Jun 2007
278 Beiträge
 
Delphi 2009 Professional
 
#6

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 22:56
Ah danke.
Ich versuche es immer noch auf dem klassischen Weg.
Mir ist ne Idee gekommen.

Ist es möglich ein temporäres Feld einzuführen bei dem die Datensätze laufend nummeriert werden in der reihenfolge in der ich sie bei der 1. Abfrage sortiere?

Da könnte ich feststellen an welcher Position sich mein gesuchter datensatz mit Nummern ausgedrückt befindet und danach in einer Unterabfrage den Wertebereich einschränken.
٩๏̯͡๏)۶
  Mit Zitat antworten Zitat
omata

Registriert seit: 26. Aug 2004
Ort: Nebel auf Amrum
3.154 Beiträge
 
Delphi 7 Enterprise
 
#7

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 23:03
Verrate uns doch erstmal welches DBMS du benutzt.
  Mit Zitat antworten Zitat
Hedge

Registriert seit: 30. Jun 2007
278 Beiträge
 
Delphi 2009 Professional
 
#8

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 23:04
MySQL
٩๏̯͡๏)۶
  Mit Zitat antworten Zitat
omata

Registriert seit: 26. Aug 2004
Ort: Nebel auf Amrum
3.154 Beiträge
 
Delphi 7 Enterprise
 
#9

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 23:08
Es gibt in einer Datenbank keine Reihenfolge, es sei denn man definiert eine. Kannst du mal deine Abfrage beispielhaft zeigen? Wie sieht dein Sortierkriterium aus?
  Mit Zitat antworten Zitat
Hedge

Registriert seit: 30. Jun 2007
278 Beiträge
 
Delphi 2009 Professional
 
#10

Re: SQL: benachbarte Datensätze mitselektieren

  Alt 3. Jul 2009, 23:11
SQL-Code:
SELECT score
FROM 'user'
WHERE 'user_id'= 1
Da kriegen wir den score her, den der jeweilige User hat

Nun sollen die Daten für diesen User und die 2 nächsten die mehr punkte haben und die 2 die weniger als er haben bestimmt werden

SQL-Code:
SELECT username,score,land
FROM `user`
WHERE ?!?!?!?
ORDER BY score DESC
LIMIT 5;
٩๏̯͡๏)۶
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 3  1 23      


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 00:55 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz