import java.util.HashMap; import java.util.HashSet; import java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; public class Spinneri { // vanligvis en separat konitor // dette objektet skal tr?dene 中国竞猜网_中国足彩网-足球推荐e om public String navn; public HashMap materialer = new HashMap<>(); public int antallNoester = 0; public Lock laas = new ReentrantLock(); public Condition plassTilMerMohair = laas.newCondition(); public Condition plassTilMerSilke = laas.newCondition(); public Condition nokMaterialer = laas.newCondition(); public boolean ferdig = false; public final int ANTALL_NOESTER; public Spinneri(String navn, HashSet garntyper, int ANTALL_NOESTER) { this.navn = navn; this.ANTALL_NOESTER = ANTALL_NOESTER; for (String type : garntyper) { materialer.put(type, 0); } } public void importerMohair() { laas.lock(); // tr?dene venter her n?r én tr?d har g?tt inn i metoden. Denne tr?den "eier" da l?sen try { // vi importerer 100 gram mohair hver gang while (!ferdig && (materialer.get("Mohair") + 100) > 1000) { try { // hvis en tr?d m? vente her, kommer flere inn og venter her sammen plassTilMerMohair.await(); } catch (InterruptedException e) { System.out.println("Tr?den ble avbrutt"); } } // n?r vi er ute her, vil én tr?d g? videre if (!ferdig && (materialer.get("Mohair") + 100) <= 1000) { materialer.put("Mohair", materialer.get("Mohair") + 100); if (materialer.get("Silke") >= 7) { nokMaterialer.signalAll(); // gir beskjed til alle andre tr?der som venter p? nokMaterialer } } } finally { laas.unlock(); // unng?r deadlocks, dvs. at en metode aldri blir l?st opp igjen mens vi har ventende tr?der //Etter at l?sen er ?pnet, vil alle de oppdaterte variablene (tilstanden i programmet) bli synlige for de andre tr?dene } } public void importerSilke() { laas.lock(); // tr?dene venter her n?r én tr?d har g?tt inn i metoden try { // vi importerer 100 gram mohair hver gang while (!ferdig && (materialer.get("Silke") + 50) > 750) { try { // hvis en tr?d m? vente her, kommer flere inn og venter her sammen plassTilMerSilke.await(); } catch (InterruptedException e) { System.out.println("Tr?den ble avbrutt"); } } // n?r vi er ute her, vil én tr?d g? videre if (!ferdig && (materialer.get("Silke") + 50) <= 750) { materialer.put("Silke", materialer.get("Silke") + 50); if (materialer.get("Mohair") >= 18) { nokMaterialer.signalAll(); // gir beskjed til alle andre tr?der som venter p? nokMaterialer // signalAll() ?ker robustheten sammenlignet med signal() } } } finally { laas.unlock(); // unng?r deadlocks } } public void spinnSilkMohair() { laas.lock(); try { while (!ferdig && (materialer.get("Mohair") < 18 || materialer.get("Silke") < 7)) { try { nokMaterialer.await(); } catch (InterruptedException e) { System.out.println("Tr?den ble avbrutt"); } } // for best mulig robusthet i programmet m? vi reteste betingelsen if (!ferdig && (materialer.get("Mohair") >= 18 && materialer.get("Silke") >= 7)) { materialer.put("Mohair", materialer.get("Mohair") - 18); materialer.put("Silke", materialer.get("Silke") - 7); antallNoester++; if (antallNoester == ANTALL_NOESTER) { ferdig = true; } // vi m? huske ? signalisere dersom vi n? har nok plass til mer materialer if ((materialer.get("Mohair") + 100) <= 1000) { plassTilMerMohair.signalAll(); } if ((materialer.get("Silke") + 50) <= 750) { plassTilMerSilke.signalAll(); } } } finally { laas.unlock(); } } public int antallNoester() { laas.lock(); try { return antallNoester; } finally { laas.unlock(); } } }