Writing Core Data code with performance in mind auttaa valmistelemaan sovelluksen tulevaisuutta varten. Tietokantasi voi olla alussa pieni, mutta se voi helposti kasvaa, mikä johtaa hitaisiin kyselyihin ja käyttäjän kokemuksen vähenemiseen.
siitä lähtien, kun aloin kirjoittaa Collect by WeTransfer-sovellusta vuonna 2017, Olen kirjoittanut paljon Ydintietoihin liittyvää koodia, koskettaen sitä lähes päivittäin. Koska miljoonat käyttäjät lisäävät paljon sisältöä, Ydintietoihin liittyvän koodin suorittamisesta on tullut tärkeä taito tiimissämme.
vuosien varrella olemme kehittäneet paljon oivalluksia, joita Jaan mielelläni kanssanne 5 vinkkiä, jotka teidän tulisi tietää.
- 1: Hyödynnä taustahallitun objektin kontekstia
- tärkeää: Älä ohita NSManagedObject-ilmentymiä jonojen välillä
- 2: Tallenna hallittu objekti konteksti vain tarvittaessa
- harkitse tarkkaan, milloin haluat tallentaa muutoksesi
- 3: Nouda vain se, mitä tarvitset
- 4: Hyödynnä hakurajoja
- 5: Poista monta objektia kerralla käyttämällä NSBatchDeleteRequest
- 6: Know how to debug Core Data code
- Conclusion
1: Hyödynnä taustahallitun objektin kontekstia
yksi asia, jota emme alusta alkaen tehneet, on taustahallitun objektin kontekstin hyödyntäminen. Käytimme näkymäyhteyttä vain Ydintietoihin liittyvien tehtävien suorittamiseen: uuden sisällön lisäämiseen, sisällön poistamiseen, sisällön hakemiseen jne.
alussa sovelluksemme oli suhteellisen pieni. Pelkän näkymäkontekstin hyödyntäminen ei ollut ongelma, eikä se johtanut Ydintietoihin liittyviin näkyviin suoritusrangaistuksiin. Ilmeisesti, kun sovelluksemme alkoi kasvaa, tajusimme, että näkymäyhteys liittyi pääjonoon. Hitaat kyselyt estivät käyttöliittymämme ja sovelluksemme tuli vähemmän vastaavaksi.
yleensä paras käytäntö on suorittaa tietojenkäsittely taustajonossa, koska se voi olla SUORITINTEHOKASTA. Esimerkit, kuten JSONin tuominen Ydintietoihin, voivat muuten estää näkymäyhteyden ja johtaa reagoimattomuuteen käyttöliittymässä.
ratkaisuna on käyttää taustahallittua objektiyhteyttä. Uusimpien sovellusliittymien avulla on helppo luoda uusi konteksti pysyvästä säiliöstäsi:
let backgroundContext = persistentContainer.newBackgroundContext()
suosittelen tätä menetelmää NSManagedObjectContext(concurrenyType:)
initializerin yli, koska se liittyy automaattisesti NSPersistentStoreCoordinator
: n kanssa ja se asetetaan kuluttamaan myös NSManagedObjectContextDidSave
lähetyksiä. Tämä pitää taustayhteyden synkronoituna näkymäyhteyden kanssa.
voit tallentaa tämän taustayhteyden mukautettuun pysyvään säiliöiden alaluokkaan. Näin voit käyttää taustayhteyttä uudelleen ja sinun tarvitsee hallita vain kahta kontekstia. Tämä pitää Ydintietorakenteen yksinkertainen ymmärtää ja se estää ottaa useita epätahdissa yhteyksissä.
jos joudut käyttämään taustayhteyttä vain muutamassa kohdassa, voit myös päättää käyttää performBackgroundTask(_:)
– menetelmää, joka luo taustayhteyden paikalleen:
persistentContainer.performBackgroundTask { (backgroundContext) in // .. Core Data Code}
tämä menetelmä luo kuitenkin uuden NSManagedObjectContext
joka kerta, kun siihen vedotaan. Kannattaa harkita jaetun taustayhteyden käyttöä, jos lähetät useammin taustayhteyteen.
tärkeää: Älä ohita NSManagedObject-ilmentymiä jonojen välillä
monisäikeisen Ydintietokoodin kirjoittaminen on paljon monimutkaisempaa kuin yhden näkymäkontekstin käyttäminen. Syy tähän on se, että NSManagedObject
instantioitua ei voi noin vain siirtää katseluyhteydestä taustayhteyteen. Se johtaisi kaatumiseen ja mahdolliseen tietojen korruptioon.
kun hallittua objektia on tarpeen siirtää jonosta toiseen, voit käyttää NSManagedObjectID
-koodia, joka on kierreturvallinen:
let managedObject = NSManagedObject(context: persistentContainer.viewContext)backgroundContext.perform { let object = try? backgroundContext.existingObject(with: managedObject.objectID)}
2: Tallenna hallittu objekti konteksti vain tarvittaessa
hallitun objektin kontekstin tallentaminen toimittaa kaikki nykyiset muutokset kontekstin yläsäilöön. Kuten voitte kuvitella, tämä ei ole halpa operaatio ja sitä tulisi käyttää vain tarvittaessa suorituskyvyn varmistamiseksi Ydintiedoissa.
Ensinnäkin on tärkeää tarkistaa, onko mitään pelastettavaa. Jos muutoksia ei toimiteta, ei ole myöskään syytä tehdä tallennusta. Luomalla saveIfNeeded
– menetelmän annat itsellesi mahdollisuuden helposti sisäänrakennettuun tarkistukseen:
harkitse tarkkaan, milloin haluat tallentaa muutoksesi
lukuun ottamatta sitä, että käytät saveIfNeeded
save()
sijasta, sinun on myös harkittava, onko tallennuksessa järkeä. Vaikka asiayhteydessä voi olla muutoksia, niitä ei aina tarvitse toimittaa suoraan.
esimerkiksi, jos olet tärkeä useita kohteita tietokantaan, saatat haluta tallentaa vasta, kun olet tuonut kaikki kohteet taustayhteydestä. Tallennusta seuraa usein KÄYTTÖLIITTYMÄPÄIVITYS ja useat tallenteet toisensa jälkeen voivat helposti johtaa turhiin uudelleenlatauksiin. Sen lisäksi, että, ota huomioon, että tallennetut muutokset taustayhteydessä yhdistetään näkymäyhteyteen, estää pääjono pian samoin. Ole sen tähden tajuissasi!
3: Nouda vain se, mitä tarvitset
tietojen hakeminen on kallis tehtävä, ja sen on oltava mahdollisimman tehokas, jotta sovelluksesi on valmis suurille tietokokonaisuuksille. Seuraava koodi on usein tehty virhe:
tämä koodi Lataa kaikki syötetyt objektit muistiin, kun sitä suodatetaan suoraan sen jälkeen, jolloin jäljelle jää vain sisältöä, jolla on nimi.
on paljon performantimpaa käyttää predikaatteja vain tarvittavien objektien hakemiseen. Yllä oleva suodatin voidaan kirjoittaa seuraavasti NSPredicate
:
tällä on kaksi etua:
- Vain tarvittavat objektit ladataan muistiin
- sinun ei tarvitse iteroida kaikkia olioita
predikaatit ovat hyvin joustavia ja niiden avulla voit useimmissa tapauksissa hakea halutun tietojoukon säilyttäen kuitenkin suorituskyvyn Ydinaineistossa.
4: Hyödynnä hakurajoja
edellisen esimerkin mukaisesti on tärkeää asettaa hakurajat, kun haluat näyttää vain osan aineistosta.
esimerkiksi, että tarvitset vain 3 ensimmäistä nimeä kaikista sisältökohdista. Tällöin olisi tarpeetonta ladata kaikki sisällön kohteet, joilla on nimi muistiin. Voisimme estää tämän asettamalla noutorajan:
tämä koodi palauttaa vain ensimmäiset 3 sisältöä, joilla on nimi.
5: Poista monta objektia kerralla käyttämällä NSBatchDeleteRequest
sen sijaan, että iteroitaisiin tietojoukon yli poistamalla jokainen objekti yksitellen, on usein tehokkaampaa käyttää NSBatchDeleteRequest
, joka toimii nopeammin, koska se toimii SQL-tasolla pysyvässä säilössä itsessään.
voit lukea lisää erien poistopyynnöistä blogikirjoituksessani käyttäen Nsbatchdeleterequestiä erien poistamiseksi Ydintiedoista.
6: Know how to debug Core Data code
kuten kaikkien kirjoittamiesi koodien kohdalla on tärkeää osata optimoida ja debugata se, kun se ei toimi odotetulla tavalla. On monia tapoja virheenkorjaus, jotka parhaiten selitetään oma blogikirjoitus: Core tietojen virheenkorjaus Xcode käyttäen käynnistää argumentteja.
Conclusion
kirjoittaminen performant Core Data code alusta asti auttaa sinua valmistelemaan sovelluksen tulevia suuria datakokonaisuuksia varten. Vaikka sovellus saattaa suorittaa alussa se voi helposti hidastaa, kun tietokanta ja malli kasvaa. Käyttämällä taustayhteyttä, smart fetch-pyyntöjä ja batch delete-pyyntöjä teet Ydintietokoodistasi jo suorituskykyisemmän.
jos haluat parantaa Swift-tietämystäsi vielä enemmän, tutustu Swift-kategoriasivulle. Voit vapaasti ottaa minuun yhteyttä tai twiitata minulle Twitterissä, jos sinulla on muita vinkkejä tai palautetta.
Kiitos!