Globaler är skattsvärd för att lagra data. Träd. Del 1

Globaler är skattsvärd för att lagra data. Träd. Del 1 De riktiga databassvärden – globala – har varit kända sedan länge, men fortfarande är det få som vet hur man använder dem effektivt eller äger inte detta supervapen alls.

Om du använder globala lösningar för att lösa de problem som de är riktigt bra på, kan du uppnå enastående resultat. Antingen i produktivitet eller för att förenkla lösningen av problemet (1, 2).

Globaler är ett speciellt sätt att lagra och bearbeta data, helt annorlunda än tabeller i SQL. De dök upp 1966 på språket PÅSSJUKA) (evolutionär utveckling - Cache ObjectScript, nedan COS) i den medicinska databasen och finns fortfarande kvar används aktivt, och även trängt in i några andra områden där tillförlitlighet och hög prestanda krävs: ekonomi, handel, etc.

Globaler i moderna DBMS stödjer transaktioner, loggning, replikering och partitionering. De där. de kan användas för att bygga moderna, pålitliga, distribuerade och snabba system.

Globaler begränsar dig inte till relationsmodellen. De ger dig friheten att utveckla datastrukturer som är optimerade för specifika uppgifter. För många applikationer kan smart användning av globals verkligen vara ett hemligt vapen, som levererar prestanda som relationsapplikationsutvecklare bara kan drömma om.

Globaler som ett sätt att lagra data kan användas i många moderna programmeringsspråk, både på hög och låg nivå. Därför kommer jag i denna artikel att fokusera specifikt på globaler, och inte på språket som de en gång kom ifrån.

2. Hur globaler fungerar

Låt oss först förstå hur globala fungerar och vilka deras styrkor är. Globaler kan ses från olika synvinklar. I den här delen av artikeln kommer vi att titta på dem som träd. Eller som hierarkiska datalager.

För att uttrycka det enkelt, en global är en beständig array. En array som automatiskt sparas på disk.
Det är svårt att föreställa sig något enklare för att lagra data. I kod (i COS/M-språk) skiljer den sig från en vanlig associativ array endast i symbolen ^ före namnet.

För att spara data i en global behöver du inte lära dig SQL-frågespråket, kommandona för att arbeta med dem är mycket enkla. De kan läras in på en timme.

Låt oss börja med det enklaste exemplet. Enplansträd med 2 grenar. Exemplen är skrivna i COS.

Globaler är skattsvärd för att lagra data. Träd. Del 1

Set ^a("+7926X") = "John Sidorov"
Set ^a("+7916Y") = "Sergey Smith"



När du infogar information i en global (Set-kommando) händer 3 saker automatiskt:

  1. Sparar data till disk.
  2. Indexering. Det som står inom parentes är nyckeln (i engelsk litteratur - "subscript"), och till höger om lika är värdet ("nodvärde").
  3. Sortering. Data sorteras efter nyckel. I framtiden, när du korsar arrayen, kommer det första elementet att vara "Sergey Smith" och det andra "John Sidorov". När databasen tar emot en lista över användare från den globala slösar inte databasen tid på att sortera. Dessutom kan du begära utmatning av en sorterad lista, med början från vilken nyckel som helst, även en obefintlig (utmatningen börjar från den första riktiga nyckeln, som kommer efter den obefintliga).

Alla dessa operationer går otroligt snabbt. På min hemdator fick jag värden upp till 750 000 inserts/sek i en enda process. På flerkärniga processorer kan värdena nå tiotals miljoner skär/sek.

Självklart säger själva insättningshastigheten inte så mycket. Du kan till exempel väldigt snabbt skriva in information i textfiler – så här ryktas Visumhantering fungerar. Men i fallet med globala får vi en strukturerad indexerad lagring som ett resultat, som enkelt och snabbt kan arbetas med i framtiden.

Globaler är skattsvärd för att lagra data. Träd. Del 1

  • Globals största styrka är hastigheten med vilken nya noder kan infogas.
  • Data i det globala indexeras alltid. Att korsa dem, både på en nivå och djupt in i trädet, går alltid snabbt.

Låt oss lägga till några fler grenar av den andra och tredje nivån till den globala.

Set ^a("+7926X", "city") = "Moscow"
Set ^a("+7926X", "city", "street") = "Req Square"
Set ^a("+7926X", "age") = 25
Set ^a("+7916Y", "city") = "London"
Set ^a("+7916Y", "city", "street") = "Baker Street"
Set ^a("+7916Y", "age") = 36

Globaler är skattsvärd för att lagra data. Träd. Del 1

Det är uppenbart att träd på flera nivåer kan byggas utifrån globaler. Dessutom är åtkomst till valfri nod nästan omedelbar på grund av automatisk indexering under infogning. Och på vilken nivå som helst i trädet sorteras alla grenar efter nyckel.

Som du kan se kan information lagras i både en nyckel och ett värde. Den totala nyckellängden (summan av längderna för alla index) kan nå 511 byte, och värdena 3.6 MB för cache. Antalet nivåer i trädet (antal dimensioner) är 31.

En annan intressant punkt. Du kan bygga ett träd utan att ange värdena för noderna på de övre nivåerna.

Globaler är skattsvärd för att lagra data. Träd. Del 1

Set ^b("a", "b", "c", "d") = 1
Set ^b("a", "b", "c", "e") = 2
Set ^b("a", "b", "f", "g") = 3

Tomma cirklar är noder som inte har något värde tilldelat.

För att bättre förstå globaler, låt oss jämföra dem med andra träd: trädgårdsträd och filsystemnamnsträd.

Låt oss jämföra träd på globaler med de mest bekanta hierarkiska strukturerna för oss: med vanliga träd som växer i trädgårdar och fält, såväl som med filsystem.

Globaler är skattsvärd för att lagra data. Träd. Del 1

Som vi ser i trädgårdsträd finns löv och frukter bara i ändarna av grenarna.
Filsystem - information lagras endast i ändarna av grenar, som är fullt kvalificerade filnamn.

Och här är den globala datastrukturen.

Globaler är skattsvärd för att lagra data. Träd. Del 1Skillnader:

  1. Interna noder: information i en global kan lagras i varje nod, inte bara i ändarna av grenar.
  2. Externa noder: Den globala måste ha definierade värden i ändarna av grenarna, medan FS och trädgårdsträd inte har det.



När det gäller interna noder kan vi säga att strukturen för det globala är en superset av strukturen för namnträd i filsystem och trädgårdsträd. De där. mer flexibel.

I allmänhet är det globala beställt träd med möjlighet att lagra data i varje nod.

För att bättre förstå globalernas arbete, föreställ dig vad som skulle hända om skaparna av filsystem använde ett tillvägagångssätt som liknar globala för att lagra information?

  1. Att ta bort en enda fil i en katalog skulle automatiskt radera katalogen, såväl som alla överliggande kataloger som bara innehåller den katalog som just tagits bort.
  2. Det skulle inte behövas kataloger. Det skulle helt enkelt finnas filer med underfiler och filer utan underfiler. Om man jämför med ett vanligt träd, skulle varje gren bli en frukt.

    Globaler är skattsvärd för att lagra data. Träd. Del 1

  3. Saker som README.txt-filer kanske inte behövs. Allt som behövdes sägas om innehållet i katalogen kunde skrivas in i själva katalogfilen. I sökvägsutrymmet är filnamnet omöjligt att skilja från katalognamnet, så det gick att klara sig med bara filer.
  4. Hastigheten att ta bort kataloger med kapslade underkataloger och filer skulle öka dramatiskt. Många gånger på Habré har det funnits artiklar om hur länge och svårt det är att radera miljontals små filer (1, 2). Men om du skapar ett pseudo-filsystem på ett globalt, kommer det att ta sekunder eller bråkdelar av det. När jag testade att ta bort underträd på en hemdator tog den bort 1-96 miljoner noder från ett tvåskiktsträd på en hårddisk (inte SSD) på 341 sekund. Dessutom talar vi om att ta bort en del av trädet, och inte bara hela filen med globaler.

Globaler är skattsvärd för att lagra data. Träd. Del 1
Att ta bort underträd är en annan stark punkt för globala. Du behöver ingen rekursion för detta. Detta sker otroligt snabbt.

I vårt träd kunde detta göras med kommandot Döda.

Kill ^a("+7926X")

Globaler är skattsvärd för att lagra data. Träd. Del 1

För en bättre förståelse av vilka åtgärder som är tillgängliga för oss över globala, kommer jag att ge en kort tabell.

Grundläggande kommandon och funktioner för att arbeta med globaler i COS

uppsättning
Ställa in förgreningar till en nod (om inte ännu definierad) och nodvärden

Sammanfoga
Kopiera ett underträd

Döda
Ta bort ett underträd

ZKill
Ta bort värdet för en specifik nod. Underträdet som kommer ut från noden berörs inte

$Query
Fullständig korsning av trädet, gå djupt in i trädet

$Order
Att korsa grenar av en specifik nod

$Data
Kontrollera om en nod är definierad

$Inkrement
Atomiskt inkrementerande ett nodvärde. För att undvika att läsa och skriva, för ACID. Nyligen har det rekommenderats att byta till $Sequence

Tack för din uppmärksamhet, vi är redo att svara på dina frågor.

Villkor: Den här artikeln och mina kommentarer till den är min åsikt och har inget samband med InterSystems Corporations officiella position.

Förlängning Globaler är skattsvärd för att lagra data. Träd. Del 2. Du kommer att lära dig vilka typer av data som kan visas på globala enheter och på vilka uppgifter de ger maximal nytta.

Källa: will.com

Lägg en kommentar