MoniquE: Tiefste freie ID ermitteln

Hallo liebe Forianer

Ich habe eine Tabelle mit sagen wir 100 ID's. Nun lösche ich Datensatz Nummer 45. Somit ist diese ID wieder frei, während alle anderen 99 (1-100) noch belegt sind.

Meine Frage ist nun: Wie finde ich die tiefste freie ID einer mySQL-Tabelle raus? Muss ich das mit "While" lösen? (Das wäre bei mehreren tausend ID's sicherlich nicht so schnell. Gibt es einen schnelleren Ansatz?

Weil mir die Forum-Suche und Onkel Google nicht helfen konnten, wende ich mich nun an Euch.

Schon mal herzlichen Dank für jeden Hinweis.

Liebe Grüsse
MoniquE

  1. SELECT id FROM tabelle ORDER BY id DESC LIMIT 0,1

    Ist vielleicht nicht die eleganteste Lösung, müsste aber funktionieren.

    1. Ist vielleicht nicht die eleganteste Lösung, müsste aber funktionieren.

      das liefert die kleinste vergebene, nicht aber die kleinste NICHT vergebene ;)

      1. das liefert die kleinste vergebene, nicht aber die kleinste NICHT vergebene ;)

        die größte natürlich

      2. das liefert die kleinste vergebene, nicht aber die kleinste NICHT vergebene ;)

        Ohja du hast recht, da habe ich mich wohl verlesen :)

  2. Sup!

    Ich habe eine Tabelle mit sagen wir 100 ID's. Nun lösche ich Datensatz Nummer 45. Somit ist diese ID wieder frei, während alle anderen 99 (1-100) noch belegt sind.

    Erzeugst Du diese ID-Spalte selbst, oder kommt die per automatischem Index o.ä. zustande?

    Meine Frage ist nun: Wie finde ich die tiefste freie ID einer mySQL-Tabelle raus? Muss ich das mit "While" lösen? (Das wäre bei mehreren tausend ID's sicherlich nicht so schnell. Gibt es einen schnelleren Ansatz?

    Bei Datenbank-vergebenen IDs ist es immer oder zumindest oft so, dass die IDs nicht wieder frei werden, damit man z.B. erkennen kann, dass ein Datensatz, der mal vorhanden war, eben nicht mehr da ist, und nicht fälschlicherweise den neuen Datensatz für den alten hält.

    Gruesse,

    Bio

    --
    Never give up, never surrender!!!
  3. echo $begrüßung;

    Meine Frage ist nun: Wie finde ich die tiefste freie ID einer mySQL-Tabelle raus?

    Dieser Wunsch wird gern von Anfängern geäußert. Da es aber im Allgemeinen nicht sinnvoll ist, und viel mehr Argumente dagegen als dafür sprechen ist das auch nicht vorgesehe. Hinzu kommt noch, dass man in einem DBMS zwar wunderbar nach vorhandenen Daten suchen kann, aber das Aufspüren nicht vorhandener Daten nicht vorgesehen und damit kaum bis gar nicht unterstützt ist. Ich wüsste keine andere einfache Methode, als einzeln und aufsteigend nach dem Vorhandensein der IDs zu forschen und beim ersten Misserfolg anzuhalten. Es fallen mit nur noch kompliziertere, dafür aber u.U. schnellere Algorithmen ein. Doch all das ist gegenüber dem Ignorieren der Lücken viel zu aufwändig.

    Als ID wird oft, und auch in deinem Fall, ein Integer-Wert verwendet. Wie groß ist denn der Wertebereich, den deine ID annehmen kann, und wie groß die zu erwartende Datenmenge? Meinst du, dass die zur Verfügung stehende Anzahl nicht ausreichend sind?

    echo "$verabschiedung $name";

  4. Mahlzeit,

    Ich habe eine Tabelle mit sagen wir 100 ID's. Nun lösche ich Datensatz Nummer 45. Somit ist diese ID wieder frei, während alle anderen 99 (1-100) noch belegt sind.

    Und diese jetzt wieder "frei gewordene" ID möchtest Du für einen neuen Datensatz mit möglicherweise - und sogar recht höchstwahrscheinlich - ganz anderen Daten verwenden?

    Das ist - wie dedlfix schon bemerkte - eine GANZ schlechte ID (das Wortspiel musste einfach sein *g*). Stell Dir nur mal folgenden Fall vor:

    Du hast eine Tabelle mit Kunden und eine mit Bestellungen. In der Tabelle "kunden" hast Du einen Datensatz mit der ID 42, "Karl Klapp". Karl Klapp hat auch Bestellungen getätigt, so dass in der Tabelle "bestellungen" mehrere Einträge mit der "kundenid" 42 vorhanden sind.

    Wenn Karl Klapp jetzt nicht mehr Kunde ist und Du den Datensatz löschst, dann bekommst Du einerseits erstmal Inkonsistenzen in Deiner Anwendung, weil Du Bestellungen hast, die eine nicht (mehr) existierende "kundenid" besitzen (außer natürlich, Du löschst diese Bestellungen kaskadierend gleich mit). Und andererseits und weiterhin hast Du, wenn Du dann diese "kundenid" 42 für einen neuen Kunden (nennen wir ihn "Hans Schranz") wiederverwendest, absolut falsche Informationen in der Datenbank - weil dann nämlich dort drinsteht, dass Hans Schranz schon ganz viel bestellt hat ... was er ja aber gar nicht hat, sondern Karl Klapp, der diese ID vorher hatte.

    Grundsätzlich ist bei mehreren voneinander abhängigen Tabellen mit Fremdschlüsselbeziehungen eindeutig davon abzuraten, einen Datensatz wirklich jemals physisch zu löschen ... Löschkennzeichen setzen OK, inaktiv schalten OK, aber richtig löschen: niemals!

    Viel schlimmer ist jedoch, eine einstmals vergebene ID wiederaufleben zu lassen, weil Du Dir dadurch im Normalfall mehr Probleme einhandelst, als Du Dir dadurch Vorteile verschaffst (ich wüsste im Moment nicht einmal einen einzigen Vorteil, den so ein Vorgehen hätte).

    Achja: und mit PHP hat das Ganze nun wirklich ÜBERHAUPT NICHTS zu tun ... :-)

    MfG,
    EKKi

    --
    sh:( fo:| ch:? rl:( br:> n4:~ ie:% mo:} va:) de:] zu:) fl:{ ss:) ls:& js:|
  5. Hallo,

    Meine Frage ist nun: Wie finde ich die tiefste freie ID einer mySQL-Tabelle raus?

    Indem du den Satz nicht löscht, sondern als gelöscht markierst, z.B. loe_kz = 1

    und dann
    SELECT id FROM xxx WHERE loe_kz=1 ORDER BY id LIMIT 0,1

    Da ist er!

    Kalle

  6. Danke an Euch! Ihr habt recht: Eine einmal vergebene ID 'darf' nicht wieder vergeben werden. Das macht echt keinen Sinn.

    Danke & Gruss
    MoniquE

    1. Hello,

      Danke an Euch! Ihr habt recht: Eine einmal vergebene ID 'darf' nicht wieder vergeben werden. Das macht echt keinen Sinn.

      Deshalb ist die Aufgabe, Lücken in einem (ordinalen) Schlüsselkreis zu finden trotzdem sinnvoll!

      Ein harzliches Glückauf

      Tom vom Berg

      --
      Nur selber lernen macht schlau
      http://bergpost.annerschbarrich.de
  7. Hello,

    Mit MySQL 5.x getestet:

    mit diesem Statement kannst Du Lücken im Nummernkreis finden

    select a.id from zahl a
       left join zahl b on (b.id = a.id +1)
       where b.id is NULL
       order by a.id;

    Liefert die ID, _nach_ der eine Lücke besteht.
    Die Lücke kann durchaus größer als ein ordinales Element sein.

    Die letzte gefundene ID ist dann freilich die größte vorhandene, denn danach klafft dann die Mammutlücke...

    Ob _vor_ der ersten vorhandenen ID Elemente im Nummernkreis fehlen, musst Du in einem zweiten Statement herausfinden.

    Ein harzliches Glückauf

    Tom vom Berg

    --
    Nur selber lernen macht schlau
    http://bergpost.annerschbarrich.de