Lücken in einem Indexfeld in einer Tabelle finden

Sigma

Neuer Benutzer
Beiträge
1
Feld: Barcode
Tabelle: Archiv

Ich benötige eine mySQL Abfrage, die mir alle Lücken ab 10.000 bis 1.000.000 ausgibt.

Wenn beispielsweise 10.000, 10.001, 10.002, 10.004, 10.005 im Feld Barcode sind, benötigt ich die Ausgabe 10.003.
Kann ich diese Abfrage ohne Zusatzfeld und Zusatztabelle als SELECT formulieren?
 
Werbung:
Feld: Barcode
Tabelle: Archiv

Ich benötige eine mySQL Abfrage, die mir alle Lücken ab 10.000 bis 1.000.000 ausgibt.

Wenn beispielsweise 10.000, 10.001, 10.002, 10.004, 10.005 im Feld Barcode sind, benötigt ich die Ausgabe 10.003.
Kann ich diese Abfrage ohne Zusatzfeld und Zusatztabelle als SELECT formulieren?


Das geht relativ einfach, allerdings wohl nicht in MySQL.

Du hast:

Code:
test=*# select * from sigma ;
 i
---
 2
 3
 5
 6
 9
(5 rows)

und suchst alle fehlenden Zahlen zwischen 1 und 10:

Code:
test=*# select alle_zahlen.s as fehlende_zahlen from sigma right join (select generate_Series(1,10) s) alle_zahlen on sigma.i=alle_zahlen.s where sigma.i is null;
 fehlende_zahlen
-----------------
  1
  4
  7
  8
  10
(5 rows)

MySQL kennt vieles nicht, so auch so nützliche Funktionen wie generate_series(). Mußt Dir halt 'ne extra Tabelle frickeln, die alle Zahlen enthält, und dann darauf den JOIN anwenden.
 
... Mußt Dir halt 'ne extra Tabelle frickeln, die alle Zahlen enthält, und dann darauf den JOIN anwenden.

Kann man denn so eine Tabelle auch schnell über den SQL-Server mittels einer einfachen "CREATE TABLE Zahlentabelle ..." erstellen? Oder muss ich über den Client über die INSERT INTO-Anweisung alle Zahlen - wie jetzt z.B. in dem Beispiel von 10.000 bis 1.000.000 - an den Server senden?
 
Kann man denn so eine Tabelle auch schnell über den SQL-Server erstellen mittels einer einfachen "CREATE TABLE Zahlentabelle ..." erstellen? Oder muss ich über den Client über die INSERT INTO-Anweisung alle Zahlen - wie jetzt z.B. in dem Beispiel von 10.000 bis 1.000.000 - an den Server senden?

Da MySQL ein generate_series() nicht kann wirst irgendwie anders eine Schleife machen müssen - entweder als stored Proc oder in PHP oder mit einem Editor ...
 
TSQL kann auch Schleifen, etc. das reicht um die Tabelle zu befüllen:
Code:
DECLARE   @i INT

SET     @i = 10000

WHILE @i <= 1000000
BEGIN
   INSERT INTO tabelle(spalte) VALUES (@i)

   SET     @i = @i +1
END
 
Mir fallen da auch noch zwei (zugegebenermassen grausige) Tricks ein:

  • Du generierst dir eine Hilfstabelle mit den vollständigen Zahlen und machst dann einen NOT IN (SELECT barcode FROM hilfstabelle)
  • Falls du dir sicher bist, dass immer nur eine einzige Zahl fehlt (und nie zwei) dann ginge auch ein Konstrukt wie (bitte selber ausprobieren, hab es nicht getestet!):
    Code:
    SELECT barcode+1
    FROM tabelle
    WHERE barcode+1 not in (select barcode from tabelle)
    ORDER BY barcode;
 
In beiden Fällen muss leider erst eine Hilfstabelle erzeugt werden. Mit:
Code:
WITH t AS (   SELECT   1 AS nr
       UNION ALL
       SELECT   t.nr + 1 AS nr
       FROM   t
       WHERE   t.nr < 100 )
SELECT   t.nr
FROM   t
ließe sich eine Zahlenreihe generieren aber bei der Menge an Zahlen macht es MSSQL z.B. schonmal nicht da jede weitere Zahl eine weitere rekursive Ebene bedeutet und das mag er nicht :)
 
In beiden Fällen muss leider erst eine Hilfstabelle erzeugt werden. Mit:
Code:
WITH t AS (   SELECT   1 AS nr

MySQL kann kein WITH.

ließe sich eine Zahlenreihe generieren aber bei der Menge an Zahlen macht es MSSQL z.B. schonmal nicht da jede weitere Zahl eine weitere rekursive Ebene bedeutet und das mag er nicht :)


Pffffffff.......................

Andreas
 
Werbung:
Hi,

naja, es ist nicht so das MySQL gar nicht kann. So gehts auch in MySQL / MariaDB. Dort gibt es die Storage Engine Sequence

SELECT s.seq FROM seq_10000_to_10020 s
LEFT JOIN product p ON p.barcode = s.seq
WHERE p.barcode IS NULL;

MariaDB [test]> SELECT s.seq FROM seq_10000_to_10020 s LEFT JOIN product p ON p.barcode = s.seq WHERE p.barcode IS NULL;
+-------+
| seq |
+-------+
| 10001 |
| 10002 |
| 10003 |
| 10004 |
| 10005 |
| 10006 |
| 10007 |
| 10008 |
| 10009 |
| 10010 |
| 10011 |
| 10014 |
| 10015 |
| 10016 |
| 10017 |
| 10018 |
| 10019 |
| 10020 |
+-------+
18 rows in set (0.01 sec)

Gruss

Bernd
 
Zurück
Oben