Notice: This page requires JavaScript to function properly.
Please enable JavaScript in your browser settings or update your browser.
Oppiskele CopyOnWrite-Kokoelma | Synkronoidut Kokoelmat
Monisäikeisyys Javassa

bookCopyOnWrite-Kokoelma

Olemme tutkineet monia synkronoituja kokoelmia, ja jos olet hallinnut muut, tämä on vieläkin suoraviivaisempi.

Käytännön esimerkki

Verkkosovellus, joka käyttää CopyOnWriteArrayList-kokoelmaa tapahtumatilaajien tallentamiseen. Useat säikeet voivat samanaikaisesti hakea nykyisten tilaajien listan ilmoittaakseen heille muutoksista, kun taas toiset säikeet voivat lisätä tai poistaa tilaajia.

Erot muihin tyyppeihin

CopyOnWrite-kokoelmat luovat kopion kokoelmasta aina, kun siihen tehdään muutos. Tämä varmistaa, että lukuoperaatiot eivät esty tietojen muutosten vuoksi, tarjoten näin säieturvallisuuden lukemiseen, vaikka kirjoitusoperaatiot eivät ole säieturvallisia, koska ne tapahtuvat kokoelman erillisessä kopiossa.

CopyOnWrite-näkymät:

Note
Huomio

Kuten kuvasta näemme, kun lisätään uusi alkio, tehdään kopio tästä tietorakenteesta. Kaikki säikeet, jotka käyttivät tätä kokoelmaa ennen muutosta, jatkavat toimintaansa ongelmitta, koska nämä muutokset eivät vaikuta heidän käyttämäänsä CopyOnWrite-kopioon!

CopyOnWriteArraySet

CopyOnWriteArraySet on säieturvallinen setin toteutus, joka perustuu CopyOnWriteArrayList-luokkaan. Se varmistaa säieturvallisuuden luomalla uuden kopion pohjasetistä aina, kun tapahtuu muutos, kuten alkion lisääminen tai poistaminen.

Tämä lähestymistapa on erityisen hyödyllinen, kun settiä luetaan usein ja muutetaan harvoin, sillä se tarjoaa kaikille säikeille yhtenäisen näkymän setistä ilman, että tarvitaan synkronointia.

CopyOnWriteArrayList

CopyOnWriteArrayList on säieturvallinen versio ArrayList-luokasta, joka varmistaa säieturvallisuuden luomalla uuden kopion taustalla olevasta taulukosta aina, kun sitä muokataan.

Tämä rakenne tarjoaa vikatolerantin iteraattorin, joka ei heitä ConcurrentModificationException-poikkeusta, koska se toimii tilannekuvalla taulukosta, joka otettiin iteraattorin luontihetkellä. Se soveltuu parhaiten tilanteisiin, joissa lukuoperaatioita tehdään huomattavasti useammin kuin kirjoitusoperaatioita, sillä koko taulukon kopioiminen jokaisen kirjoituksen yhteydessä voi olla raskasta.

Käytännön esimerkki käyttötapauksesta

CopyOnWrite-kokoelman metodit

addIfAbsent(E e): Lisää alkion listaan vain, jos sitä ei ole jo listassa/monikossa.

Main.java

Main.java

copy
123456789101112131415161718192021
package com.example; import java.util.concurrent.CopyOnWriteArrayList; public class Main { public static void main(String[] args) { CopyOnWriteArrayList<String> list = new CopyOnWriteArrayList<>(); list.add("apple"); list.add("banana"); // Attempt to add a duplicate element list.addIfAbsent("apple"); // This will not add "apple" again // Adding a new element list.addIfAbsent("orange"); // This will add "orange" System.out.println(list); // Output: [apple, banana, orange] } }

Tässä esimerkissä "apple" ei lisätä uudelleen, koska se on jo olemassa listassa. addIfAbsent() metodi estää kaksoiskappaleiden lisäämisen ja säilyttää alkioiden yksilöllisyyden.

addAllAbsent(Collection<? extends E> c): Lisää kaikki alkiot annetusta kokoelmasta listaan/monikkoon, ohittaen jo olemassa olevat alkiot.

Main.java

Main.java

copy
12345678910111213141516171819202122
package com.example; import java.util.Arrays; import java.util.List; import java.util.concurrent.CopyOnWriteArrayList; public class Main { public static void main(String[] args) { CopyOnWriteArrayList<String> list = new CopyOnWriteArrayList<>(); list.add("apple"); list.add("banana"); List<String> newFruits = Arrays.asList("banana", "cherry", "date"); // Adding elements from the collection, ignoring duplicates list.addAllAbsent(newFruits); System.out.println(list); // Output: [apple, banana, cherry, date] } }

Tässä esimerkissä "banana" on jo olemassa listassa, joten addAllAbsent() ei lisää sitä uudelleen. Metodi varmistaa, että vain ainutlaatuiset alkiot annetusta kokoelmasta lisätään listaan.

Note
Huomio

Kaikki muut CopyOnWrite-kokoelmien metodit ovat samanlaisia kuin niiden yliluokkien metodit; ne vain kopioivat kokoelman tilan aina kun muutoksia tehdään.

Rajoitukset ja Edut

😔Rajoitukset:

CopyOnWrite-kokoelmilla on merkittäviä rajoituksia. Ne aiheuttavat muistikustannuksia, koska kokoelmasta luodaan uusi kopio aina, kun siihen tehdään muutos, mikä voi olla merkittävää. Tämä rakenne tekee niistä vähemmän sopivia tilanteisiin, joissa tarvitaan usein datan muutoksia.

💪Edut:

Toisaalta CopyOnWrite kokoelmat tarjoavat huomattavia etuja. Ne ovat erittäin tehokkaita datan lukemisessa monisäikeisessä ympäristössä. Nämä kokoelmat toimivat poikkeuksellisen hyvin tilanteissa, joissa lukuoperaatioita on huomattavasti enemmän kuin kirjoitusoperaatioita, mikä tekee niistä erinomaisen valinnan tällaisiin käyttötapauksiin.

Note
Huomio

Kuitenkin, koska kopiointi tapahtuu jokaisen muutoksen yhteydessä, CopyOnWrite-kokoelmat voivat kuluttaa enemmän muistia eivätkä sovellu tilanteisiin, joissa on usein kirjoitusoperaatioita. Ne ovat tehokkaimpia silloin, kun lukuoperaatioita on enemmän kuin kirjoitusoperaatioita.

1. Mitä tapahtuu, kun kutsut addIfAbsent(E e)-metodia CopyOnWriteArrayList-luokassa?

2. Miksi CopyOnWrite-kokoelmat soveltuvat erityisesti tilanteisiin, joissa lukuoperaatioita on paljon ja tietoa muutetaan harvoin?

question mark

Mitä tapahtuu, kun kutsut addIfAbsent(E e)-metodia CopyOnWriteArrayList-luokassa?

Select the correct answer

question mark

Miksi CopyOnWrite-kokoelmat soveltuvat erityisesti tilanteisiin, joissa lukuoperaatioita on paljon ja tietoa muutetaan harvoin?

Select the correct answer

Oliko kaikki selvää?

Miten voimme parantaa sitä?

Kiitos palautteestasi!

Osio 2. Luku 7

Kysy tekoälyä

expand

Kysy tekoälyä

ChatGPT

Kysy mitä tahansa tai kokeile jotakin ehdotetuista kysymyksistä aloittaaksesi keskustelumme

Awesome!

Completion rate improved to 3.33

bookCopyOnWrite-Kokoelma

Pyyhkäise näyttääksesi valikon

Olemme tutkineet monia synkronoituja kokoelmia, ja jos olet hallinnut muut, tämä on vieläkin suoraviivaisempi.

Käytännön esimerkki

Verkkosovellus, joka käyttää CopyOnWriteArrayList-kokoelmaa tapahtumatilaajien tallentamiseen. Useat säikeet voivat samanaikaisesti hakea nykyisten tilaajien listan ilmoittaakseen heille muutoksista, kun taas toiset säikeet voivat lisätä tai poistaa tilaajia.

Erot muihin tyyppeihin

CopyOnWrite-kokoelmat luovat kopion kokoelmasta aina, kun siihen tehdään muutos. Tämä varmistaa, että lukuoperaatiot eivät esty tietojen muutosten vuoksi, tarjoten näin säieturvallisuuden lukemiseen, vaikka kirjoitusoperaatiot eivät ole säieturvallisia, koska ne tapahtuvat kokoelman erillisessä kopiossa.

CopyOnWrite-näkymät:

Note
Huomio

Kuten kuvasta näemme, kun lisätään uusi alkio, tehdään kopio tästä tietorakenteesta. Kaikki säikeet, jotka käyttivät tätä kokoelmaa ennen muutosta, jatkavat toimintaansa ongelmitta, koska nämä muutokset eivät vaikuta heidän käyttämäänsä CopyOnWrite-kopioon!

CopyOnWriteArraySet

CopyOnWriteArraySet on säieturvallinen setin toteutus, joka perustuu CopyOnWriteArrayList-luokkaan. Se varmistaa säieturvallisuuden luomalla uuden kopion pohjasetistä aina, kun tapahtuu muutos, kuten alkion lisääminen tai poistaminen.

Tämä lähestymistapa on erityisen hyödyllinen, kun settiä luetaan usein ja muutetaan harvoin, sillä se tarjoaa kaikille säikeille yhtenäisen näkymän setistä ilman, että tarvitaan synkronointia.

CopyOnWriteArrayList

CopyOnWriteArrayList on säieturvallinen versio ArrayList-luokasta, joka varmistaa säieturvallisuuden luomalla uuden kopion taustalla olevasta taulukosta aina, kun sitä muokataan.

Tämä rakenne tarjoaa vikatolerantin iteraattorin, joka ei heitä ConcurrentModificationException-poikkeusta, koska se toimii tilannekuvalla taulukosta, joka otettiin iteraattorin luontihetkellä. Se soveltuu parhaiten tilanteisiin, joissa lukuoperaatioita tehdään huomattavasti useammin kuin kirjoitusoperaatioita, sillä koko taulukon kopioiminen jokaisen kirjoituksen yhteydessä voi olla raskasta.

Käytännön esimerkki käyttötapauksesta

CopyOnWrite-kokoelman metodit

addIfAbsent(E e): Lisää alkion listaan vain, jos sitä ei ole jo listassa/monikossa.

Main.java

Main.java

copy
123456789101112131415161718192021
package com.example; import java.util.concurrent.CopyOnWriteArrayList; public class Main { public static void main(String[] args) { CopyOnWriteArrayList<String> list = new CopyOnWriteArrayList<>(); list.add("apple"); list.add("banana"); // Attempt to add a duplicate element list.addIfAbsent("apple"); // This will not add "apple" again // Adding a new element list.addIfAbsent("orange"); // This will add "orange" System.out.println(list); // Output: [apple, banana, orange] } }

Tässä esimerkissä "apple" ei lisätä uudelleen, koska se on jo olemassa listassa. addIfAbsent() metodi estää kaksoiskappaleiden lisäämisen ja säilyttää alkioiden yksilöllisyyden.

addAllAbsent(Collection<? extends E> c): Lisää kaikki alkiot annetusta kokoelmasta listaan/monikkoon, ohittaen jo olemassa olevat alkiot.

Main.java

Main.java

copy
12345678910111213141516171819202122
package com.example; import java.util.Arrays; import java.util.List; import java.util.concurrent.CopyOnWriteArrayList; public class Main { public static void main(String[] args) { CopyOnWriteArrayList<String> list = new CopyOnWriteArrayList<>(); list.add("apple"); list.add("banana"); List<String> newFruits = Arrays.asList("banana", "cherry", "date"); // Adding elements from the collection, ignoring duplicates list.addAllAbsent(newFruits); System.out.println(list); // Output: [apple, banana, cherry, date] } }

Tässä esimerkissä "banana" on jo olemassa listassa, joten addAllAbsent() ei lisää sitä uudelleen. Metodi varmistaa, että vain ainutlaatuiset alkiot annetusta kokoelmasta lisätään listaan.

Note
Huomio

Kaikki muut CopyOnWrite-kokoelmien metodit ovat samanlaisia kuin niiden yliluokkien metodit; ne vain kopioivat kokoelman tilan aina kun muutoksia tehdään.

Rajoitukset ja Edut

😔Rajoitukset:

CopyOnWrite-kokoelmilla on merkittäviä rajoituksia. Ne aiheuttavat muistikustannuksia, koska kokoelmasta luodaan uusi kopio aina, kun siihen tehdään muutos, mikä voi olla merkittävää. Tämä rakenne tekee niistä vähemmän sopivia tilanteisiin, joissa tarvitaan usein datan muutoksia.

💪Edut:

Toisaalta CopyOnWrite kokoelmat tarjoavat huomattavia etuja. Ne ovat erittäin tehokkaita datan lukemisessa monisäikeisessä ympäristössä. Nämä kokoelmat toimivat poikkeuksellisen hyvin tilanteissa, joissa lukuoperaatioita on huomattavasti enemmän kuin kirjoitusoperaatioita, mikä tekee niistä erinomaisen valinnan tällaisiin käyttötapauksiin.

Note
Huomio

Kuitenkin, koska kopiointi tapahtuu jokaisen muutoksen yhteydessä, CopyOnWrite-kokoelmat voivat kuluttaa enemmän muistia eivätkä sovellu tilanteisiin, joissa on usein kirjoitusoperaatioita. Ne ovat tehokkaimpia silloin, kun lukuoperaatioita on enemmän kuin kirjoitusoperaatioita.

1. Mitä tapahtuu, kun kutsut addIfAbsent(E e)-metodia CopyOnWriteArrayList-luokassa?

2. Miksi CopyOnWrite-kokoelmat soveltuvat erityisesti tilanteisiin, joissa lukuoperaatioita on paljon ja tietoa muutetaan harvoin?

question mark

Mitä tapahtuu, kun kutsut addIfAbsent(E e)-metodia CopyOnWriteArrayList-luokassa?

Select the correct answer

question mark

Miksi CopyOnWrite-kokoelmat soveltuvat erityisesti tilanteisiin, joissa lukuoperaatioita on paljon ja tietoa muutetaan harvoin?

Select the correct answer

Oliko kaikki selvää?

Miten voimme parantaa sitä?

Kiitos palautteestasi!

Osio 2. Luku 7
some-alt