Als u een foutmelding krijgt "Msg 8115, Level 16 Rekenkundige overloopfout bij het converteren van IDENTITEIT naar gegevenstype... ”-fout in SQL Server, komt dit waarschijnlijk omdat u probeert om gegevens in een tabel in te voegen wanneer de IDENTITY
kolom heeft de limiet van het gegevenstype bereikt.
Een IDENTITY
kolom verhoogt automatisch de waarde die is ingevoegd bij elke nieuwe rij. Als de waarde die wordt ingevoegd buiten het bereik van het gegevenstype van de kolom valt, treedt de bovenstaande fout op.
Voorbeeld van de fout
Hier is een voorbeeld van code die resulteert in de fout:
INSERT INTO t1 VALUES ('Dog');
Resultaat:
Msg 8115, Level 16, State 1, Line 1 Arithmetic overflow error converting IDENTITY to data type tinyint.
In dit geval mijn IDENTITY
kolom gebruikt de tinyint
gegevenstype, dat een bereik heeft van 0 tot 255. De fout houdt in dat de IDENTITY
kolom probeert een waarde in te voegen die hoger is dan 255.
Dit gebeurt meestal wanneer we al 255 rijen in de kolom hebben ingevoegd en nu proberen we de 256e rij in te voegen.
Zo ziet mijn tabel eruit als ik alle rijen selecteer waar de IDENTITY
kolom is groter dan 250
:
SELECT * FROM t1
WHERE c1 > 250;
Resultaat:
+------+------+ | c1 | c2 | |------+------| | 251 | Ant | | 252 | Cow | | 253 | Bat | | 254 | Duck | | 255 | Bull | +------+------+
In dit geval c1
is mijn IDENTITY
kolom (wat toevallig het type tinyint
is) ). We kunnen zien dat IDENTITY
heeft eerder 255
gegenereerd voor de kolom, en dus is de volgende waarde die probeert in te voegen 256
(uitgaande van een incrementwaarde van 1
en geen eerder mislukte inserts). Dit veroorzaakt de bovenstaande fout, omdat 256 buiten het bereik van een tinyint
valt .
Hetzelfde probleem kan optreden met gegevenstypen van smallint
(maximale waarde van 32.767) of int
(maximale waarde van 2.147.483.647). Het kan ook gebeuren met bigint
als je genoeg rijen hebt ingevoegd (meer dan 9.223.372.036.854.775.807).
Echter, de IDENTITY
waarde komt niet altijd overeen met het aantal ingevoegde rijen. U kunt een seed-waarde instellen bij het maken van een IDENTITY
kolom, en u kunt ook een verhogingswaarde instellen. Daarom zou u de bovengrens gemakkelijk veel eerder kunnen bereiken dan het aantal inserts dat op de tafel is uitgevoerd, afhankelijk van de seed- en incrementwaarden.
Ook wordt door het verwijderen van rijen uit een tabel de IDENTITY
. niet gereset waarde (hoewel het afkappen van een tabel dat wel doet).
Daarom kunt u de bovenstaande fout nog steeds ervaren, zelfs als er veel minder rijen in de tabel zijn dan de IDENTITY
het gegevenstype van de kolom zou kunnen suggereren.
Oplossing
Een oplossing is om het gegevenstype van de IDENTITY
. te wijzigen kolom. Als het bijvoorbeeld smallint
. is , verander het in int
. Of als het al int
is , verander het in bigint
.
Een andere mogelijke oplossing zou zijn om de IDENTITY
. opnieuw in te stellen zaad naar een lagere waarde. Dit zou alleen werken als je ofwel veel rijen uit de tabel hebt verwijderd, of als de oorspronkelijke seed-waarde veel hoger was dan 1
.
Als bijvoorbeeld de IDENTITY
kolom is al een int
, maar de IDENTITY
seed begon op zeg 2,000,000,000
, kunt u de IDENTITY
. resetten zaad naar 1
, waardoor er nog eens 2 miljard rijen kunnen worden ingevoegd.
Handige functies
Hier zijn enkele functies die zeer nuttig kunnen zijn bij het identificeren van dit probleem:
IDENT_CURRENT()
– retourneert de laatste identiteitswaarde die is gegenereerd voor een opgegeven tabel of weergave op een identiteitskolom.@@IDENTITY
– Retourneert de laatst ingevoerde identiteitswaarde in de huidige sessie.IDENT_SEED()
– Retourneert de oorspronkelijke seed van een identiteitskolom.IDENT_INCR()
– Retourneert de incrementwaarde van een identiteitskolom.
Hier zijn ook 3 manieren om het gegevenstype van een kolom te krijgen voor het geval u niet zeker weet wat het gegevenstype van de kolom is.
Dezelfde fout in verschillende scenario's
Dezelfde fout (bericht 8115) kan ook optreden (met een iets ander foutbericht) wanneer u expliciet probeert te converteren tussen gegevenstypen en de oorspronkelijke waarde buiten het bereik van het nieuwe type valt. Zie "Rekenkundige overloopfout bij het converteren van int naar gegevenstype numeriek" in SQL Server repareren om dit op te lossen.
Het kan ook voorkomen wanneer u een functie gebruikt zoals SUM()
op een kolom en de berekening resulteert in een waarde die buiten het bereik van het kolomtype ligt. Zie "Rekenkundige overloopfout bij het converteren van expressie naar gegevenstype int" in SQL Server repareren om dit op te lossen.