Thread iterating peste LinkedHashMap

Am un LinkedHashMap privat care este folosit pentru citire (numai pentru citire) din diferite subiecte:

class foo {

  private LinkedHashMap map = ...;


  public publicMethodCalledFromDifferentThreads() {

     for (Object foo : map) {
        ...
     }
  }
}

Această implementare nu este sigură pentru fire și astfel bucla pentru nu se poate comporta corect. Am încercat să găsesc o soluție singur și singurul lucru pe care l-am găsit este următorul:

class foo {

  private LinkedHashMap map = ...;
  private Map.Entry[] mapEntries = map.entrySet().toArray() ...;

  public publicMethodCalledFromDifferentThreads() {

     for (int i = 0; i < mapEntries.length; i++) {
        mapEntries[i]...
        ...
     }
  }
}

Deci, în cele din urmă trebuie să am două variabile și iterația devine cu adevărat complexă. Care ar fi cel mai frumos mod de a face asta?

Mulțumiri!

3
Problema mea este că odată ce există două fire iterate pe hartă, iteratorul sare la întâmplare de la intrare la intrare. Am crezut că acest lucru este cauzat de iteratorul comun, spuneți că nu poate fi cazul?
adăugat autor Vojtěch, sursa
Bine, ai dreptate, problema a fost în altă parte, mulțumesc că m-ai arătat în altă direcție!
adăugat autor Vojtěch, sursa
Era o altă variabilă care era suprascrisă și părea că era o problemă cu iteratorul.
adăugat autor Vojtěch, sursa
@ Vojtěch Care a fost problema?
adăugat autor assylias, sursa
dacă într-adevăr citiți numai de la ea (nu modificați-o în timp ce este citit), atunci afaik, nu trebuie să fie threadsafe. Ce comportament vedeți?
adăugat autor GreyBeardedGeek, sursa

2 răspunsuri

Dacă citiți numai și obiectele care stau la baza nu sunt modificate, atât lista cât și lucrurile din listă, nu ar trebui să existe nicio problemă de filetare.

Ce problemă vă confruntați cu adevărat?

Cred că este posibil să modificați cumva LinkedHashMap.

Mai mult, cum determini firele sărind în jur? Sunteți sigur că nu vă vedeți doar ieșirea din cele două fire amestecate, care ar arăta ca sărind în jur, chiar dacă fiecare fir este iterat secvențial? De exemplu, dacă fiecare fir imprimă intrarea curentă, s-ar putea să vedeți ceva asemănător

123 12 45 345 6 ....

care este secvențială ....

3
adăugat
Vă rugăm să citiți comentariul meu la GrayBeardedGeek și pst.
adăugat autor Vojtěch, sursa
@ Vojtěch mi-a actualizat răspunsul
adăugat autor hvgotcodes, sursa
@jeremy, ah, thanx pentru a arăta asta. Eram confuz. Îndepărtat...
adăugat autor hvgotcodes, sursa
@hvgotcodes, Documentația pe care o citezi este relevantă doar pentru hărțile hash-uri conectate la comandă , care trebuie specificate în mod explicit la construirea hărții. Valoarea implicită este ordonată prin inserare, unde apelul get nu este o modificare structurală. Având în vedere simptomele, acest lucru pare a fi cazul, dar m-am gândit să subliniez distincția.
adăugat autor Jeremy, sursa

Puteți utiliza un hartă sincronizată .

private final Map map = Collections.synchronizedMap(new LinkedHashMap());

public void foo() {
    synchronized(map) {
        for(K key : map.keySet()) {
           //thread safe iteration
        }
    }
}
0
adăugat