sql >> Database teknologi >  >> RDS >> Sqlserver

Reducere SQL Server-tabelfragmentering uden at tilføje/slippe et klynget indeks?

Problem

Lad os få lidt klarhed, for dette er et almindeligt problem, et alvorligt problem for enhver virksomhed, der bruger SQL Server.

Dette problem, og behovet for CREATE CLUSTERED INDEX, er misforstået.

Enig i, at det er bedre at have et permanent Clustered Index end ikke at have et. Men det er ikke meningen, og det vil alligevel føre til en lang diskussion, så lad os lægge det til side og fokusere på det stillede spørgsmål.

Pointen er, at du har betydelig fragmentering på bunken . Du bliver ved med at kalde det et "bord", men der er ikke sådan noget på det fysiske datalager eller DataStructure-niveau. Et bord er et logisk koncept, ikke et fysisk. Det er en samling af fysiske datastrukturer. Samlingen er en af ​​to muligheder:

  • Dynge
    plus alle ikke-klyngede indekser
    plus tekst-/billedekæder

  • eller et Clustered Index
    (eliminerer Heapen og én Ikke-klyngede indeks)
    plus alle ikke-klyngede indekser
    plus tekst-/billedekæder.

Dynger bliver slemt fragmenteret; jo mere indskudt (tilfældig) Indsæt/Sletninger/Opdateringer der er, jo mere fragmentering.

Der er ingen måde at rydde op i Heapen, som den er. MS tilbyder ikke en facilitet (det gør andre leverandører).

Løsning

Vi ved dog, at Create Clustered Index omskriver og omorganiserer Heapen fuldstændigt. Metoden (ikke et trick) er derfor at oprette et grupperet indeks kun med det formål at defragmentere heapen , og slip det bagefter. Du har brug for ledig plads i db'en for table_size x 1.25.

Mens du er i gang, så brug FILLFACTOR for at reducere fremtiden fragmentering. Heapen vil derefter tage mere tildelt plads, hvilket giver mulighed for fremtidige indsættelser, sletninger og rækkeudvidelser på grund af opdateringer.

Bemærk

  1. Bemærk, at der er tre niveauer af Fragmentering; dette omhandler kun niveau III, fragmentering i heapen, som er forårsaget af Mangel på et klynget indeks

  2. Som en separat opgave kan du på et andet tidspunkt overveje implementeringen af ​​et permanent Clustered Index, som helt eliminerer fragmentering ... men det er adskilt fra det postede problem.

Svar på kommentar

Ikke helt. Jeg vil ikke kalde det en "begrænsning".

  1. Den metode, jeg har givet til at fjerne fragmenteringen i heapen, er at oprette et Clustered Index, og derefter droppe det. Dvs. midlertidigt, hvis eneste formål er at rette fragmenteringen.

  2. Implementering af et Clustered Index på bordet (permanent) er en meget bedre løsning, fordi det reducerer samlet Fragmentering (datastrukturen kan stadig blive fragmenteret, se detaljerede oplysninger i links nedenfor), hvilket er langt mindre end fragmenteringen, der forekommer i en bunke.

    • Hver tabel i en relationsdatabase (undtagen "pipe" eller "queue"-tabeller) bør have et Clustered Index for at drage fordel af dets forskellige fordele.

    • Clustered Index bør være på kolonner, der distribuerer data (undgå INSERT konflikter), aldrig indekseres på en monotont stigende kolonne, såsom Record ID, som garanterer et INSERT Hot Spot på den sidste side.

I MS SQL og Sybase ASE er der tre niveauer af Fragmentering, og inden for hvert niveau flere forskellige Typer . Husk, at når vi beskæftiger os med Fragmentering, skal vi fokusere på DataStructures, ikke på tabeller (en tabel er en samling af DataStructures, som forklaret ovenfor). Niveauerne er:

  • Niveau I • Ekstra-datastruktur
    Uden for den pågældende datastruktur, på tværs af eller i databasen.

  • Niveau II • Datastruktur
    Inden for den pågældende datastruktur, ovenstående sider (på tværs af alle sider)
    Dette er det niveau, der oftest adresseres af DBA'er.

  • Niveau III • Side
    Inden for den pågældende datastruktur inden for siderne

Disse links giver alle detaljer om Fragmentering. De er specifikke for Sybase ASE, men på det strukturelle niveau gælder oplysningerne for MS SQL.

Bemærk, at den metode, jeg har givet, er Level II, den korrigerer Level II og III Fragmentering.



  1. Brug af en trigger til at implementere en begrænsning for kontrol af fremmednøgle

  2. Er Markdown (med strip_tags) tilstrækkeligt til at stoppe XSS-angreb?

  3. Menu på flere niveauer med PHP/MySQL

  4. MySqlException på ExecuteReader ved at vælge UserID(PK)