[Java] Thread

di il
19 risposte

[Java] Thread

Ciao a tutti,
Qualcuno saprebbe spiegarmi come faccio a mandare in esecuzione due thread per volta?
Grazie

19 Risposte

  • Re: [Java] Thread

    Rossella92 ha scritto:


    Qualcuno saprebbe spiegarmi come faccio a mandare in esecuzione due thread per volta?
    Quale è il dubbio? Se hai un oggetto java.lang.Thread (non ancora avviato, chiaramente) basta invocarci start() . Tutto qui. Se ne hai 2, 3, 4, ecc... farai altrettanti start().
  • Re: [Java] Thread

    Mi spiego meglio. Devo realizzare un sistema per gestire una gara di N motociclisti, ognuno dei quali è dotato di un numero di maglia progressivo.
    La pista può contenere solo due motociclisti per volta.
    Ogni motociclista corre per un tempo casuale, arriva al traguardo e poi abbandona la pista.
    La classe Thread che modella i motociclisti l'ho implementata cosi:
    public void run() {
    try {
    gara.partenza(maglia); //riceve il numero di maglia del motociclista
    tempo = percorri(minT, maxT);
    gara.arrivo(this);
    TimeUnit.SECONDS.sleep(attesa);
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    }// run
    Mentre la classe con i Semafori è:
    public class GaraSem extends Gara {
    private Semaphore mutex = new Semaphore(1);
    private Semaphore[] motociclista;
    private int maglia1;
    private int maglia2;

    public GaraSem(int dim) {
    super(dim);
    motociclista = new Semaphore[dim];
    for (int i = 0; i < dim; i++) {
    motociclista = new Semaphore(0);
    }
    motociclista[0].release();
    motociclista[1].release();
    }// costruttore
    Ho permesso ai primi due motociclisti di partire

    @Override
    public void partenza(int m) throws InterruptedException {
    // sospende il motociclista di maglia s fin quando non è il suo turno
    System.out.println("I motociclisti " + m + " e " + (m + 1) + " attendono di partire");
    motociclista[m].acquire();
    motociclista[m+1].acquire();
    }// partenza

    @Override
    public void arrivo(Motociclista m) throws InterruptedException {
    System.out.println(
    "I motociclisti " + motocDaPartire + " e " + (motocDaPartire + 1) + " sono arrivati al traguardo");
    mutex.acquire();
    motocDaPartire += 2;
    mutex.release();
    if (motocDaPartire < numMotociclisti - 1) {
    motociclista[motocDaPartire].release();
    }
    }// arrivo
    }
  • Re: [Java] Thread

    RICORDA, il codice che posti

    DEVE ESSERE FORMATTATO

    altrimenti non te lo legge NESSUNO.

    Per farlo ci sono i tag CODICE/CODE nell' "editor completo".
  • Re: [Java] Thread

    Rossella92 ha scritto:


    La pista può contenere solo due motociclisti per volta.
    Ok, questo "suona" molto come una necessità di "sincronizzazione" tra i thread, in modo che debbano bloccarsi tranne appunto due per volta (e deduco dal tuo codice, il nocciolo della sincronizzazione sia in quel partenza() ).

    Ma come avevi detto prima "mandare in esecuzione due thread per volta" è abbastanza improprio allora (non è un problema di start() ma di sincronizzazione).

    Se hai N thread-motociclisti, però dovresti chiarire con quale CRITERIO vuoi scegliere i 2 motociclisti per volta. Come capita .. capita? Per il numero di maglia? Per la posizione in un array (es. 0 e 1 poi 2 e 3, poi ....) ?
  • Re: [Java] Thread

    Per la posizione in un array (es. 0 e 1 poi 2 e 3, poi ....) ?
    Si devono partire 0 e 1, poi 2 e 3, e così via
  • Re: [Java] Thread

    Qualcuno saprebbe darmi qualche idea su come risolverlo?
  • Re: [Java] Thread

    Rossella92 ha scritto:


    Qualcuno saprebbe darmi qualche idea su come risolverlo?
    Allora, c'è solo da ragionare un pochino. Il fatto di avere un array di oggetti Semaphore va bene. Ciascun motociclista-thread da quanto deduco "sa" già quale è la sua maglia, presumo che quando crei i motociclisti gli passi tu un indice progressivo da 0. Se così, anche questo va bene.

    Il punto è che in partenza() non devi fare 2 acquire. Solo uno, quello relativo a quel motociclista. Se il semaforo è tale per cui può passare, ok, altrimenti sta lì bloccato.
    Quando crei l'oggetto GaraSem ha senso fare in modo che i primi 2 semafori ([0] e [1]) abbiano già il permit (permesso) disponibile, così chi tra i motociclisti invoca partenza(0) e partenza(1) può "partire" subito.

    Le questioni semmai sono sul arrivo(). All'inizio hai detto che "la pista può contenere solo due motociclisti per volta". Ma due nel senso della coppia per intero o due qualunque?
    Mi spiego meglio: la coppia 0-1 è partita, non sai quale dei due arriva prima. Vuoi far partire la coppia 2-3 SOLO quando entrambi i motociclisti 0-1 sono arrivati .... o è sufficiente che se quello 0 è arrivato, allora può partire il 2 (indipendentemente da quando arriva il 1, che farà poi partire il 3) ??

    Questo è il punto che a me non è chiaro. Per il resto ho chiarito qualcosa? Appena ho tempo provo a scriverlo anche io per vedere quali inghippi eventualmente mi saltano fuori.
  • Re: [Java] Thread

    Vuoi far partire la coppia 2-3 SOLO quando entrambi i motociclisti 0-1 sono arrivati
    Si dovrebbe essere proprio così. Quindi non so come rilasciare il semaforo per far in modo che partano le coppie successive.
    Si poi per il resto avevo già assegnato ad ogni Motociclista l’indice progressivo all’interno del costruttore.
  • Re: [Java] Thread

    Rossella92 ha scritto:


    Vuoi far partire la coppia 2-3 SOLO quando entrambi i motociclisti 0-1 sono arrivati
    Si dovrebbe essere proprio così. Quindi non so come rilasciare il semaforo per far in modo che partano le coppie successive.
    Se è così, ci sono almeno 2 possibilità.

    a) Usi 1 semaforo per ciascuna coppia. Ovvero hai metà semafori rispetto al numero di motociclisti. Ovviamente ciascun semaforo in questo caso dovrà consentire 2 permessi. Il arrivo() però è più semplice: non sai in che ordine 0 e 1 arrivano ma ciascuno rilascierà il permesso. Quando il semaforo ha di nuovo 2 permessi disponibili vuol dire che 0-1 sono arrivati, quindi dai 2 permessi al semaforo per i motociclisti 2-3

    b) Tieni 1 semaforo per motociclista (come stai facendo ora). Il arrivo() è solo un pochettino più complicato. Idem, non sai in che ordine 0 e 1 arrivano ma ciascuno rilascia il permesso sul SUO proprio semaforo. In arrivo() devi quindi testare se i due semafori [n+0] e [n+1] sono entrambi stati rilasciati.
    La questione è che es. arrivo() per 0 e per 1 possono arrivare teoricamente in qualunque ordine. Quindi a fronte di una invocazione di arrivo() devi determinare l'indice base (0 sia per motociclista 0 e 1) e da lì testare se i due permessi sono stati rilasciati. Se sì, allora dai i due permessi alla coppia successiva.
  • Re: [Java] Thread

    Usi 1 semaforo per ciascuna coppia. Ovvero hai metà semafori rispetto al numero di motociclisti. Ovviamente ciascun semaforo in questo caso dovrà consentire 2 permessi. Il arrivo() però è più semplice: non sai in che ordine 0 e 1 arrivano ma ciascuno rilascierà il permesso. Quando il semaforo ha di nuovo 2 permessi disponibili vuol dire che 0-1 sono arrivati, quindi dai 2 permessi al semaforo per i motociclisti 2-3
    In questo caso io dovrei fare:
    private Semaphore[]motociclisti=new Semaphore[numMotociclisti/2];
    for(int i=0;i<numMotociclisti/2;i++){
         motociclisti[i]=new Semaphore(2);
    }
    Poi nel metodo partenza
    public void partenza(int m){
        motociclisti[m].acquire();
    } 
    E nel metodo arrivo
    public void arrivo(Motociclista m){
        mutex.acquire();
        motocDaPartire++;
        System.out.println(“motociclista”+motocDaPartire+
                   “arrivato”);
        motociclisti[motocDapartire++].release(2);
        mutex.release();
    }
  • Re: [Java] Thread

    Rossella92 ha scritto:


    In questo caso io dovrei fare:
    No. Innanzitutto i Semaphore li crei con 0. Poi solo al primo [0] gli dai 2 permessi in modo che la prima coppia possa partire.

    Ma nel partenza() data la maglia devi determinare l'indice del semaforo per la coppia!! Quindi 0-->0 e 1-->0. Ovvero devi .... dividere la maglia per 2 per ottenere l'indice del semaforo.
    Idem similare nel arrivo.
  • Re: [Java] Thread

    No. Innanzitutto i Semaphore li crei con 0. Poi solo al primo [0] gli dai 2 permessi in modo che la prima coppia possa partire.
    Quindi:
    private Semaphore []motociclisti=new Semaphore[dim/2];
    for(int i=0;i<dim/2;i++){
    motociclisti[i]=new Semaphore(0);
    
    }motociclisti[0].release(2);
    Nel metodo partenza
    
    maglia=m/2;
    motociclisti[maglia].acquire();
    Nel metodo arrivo
     maglia=m.getMaglia()/2;
    mutex.acquire();
    motocDaPartire++;
    mutex.release();
    if(motocDaPartire<numMotociclisti-1)
    motociclisti[maglia].release();
  • Re: [Java] Thread

    Ho risolto aggiungendo una variabile contaM in modo che ogni volta che arriva a due rilascio il permesso per la coppia successiva
  • Re: [Java] Thread

    Rossella92 ha scritto:


    Ho risolto aggiungendo una variabile contaM in modo che ogni volta che arriva a due rilascio il permesso per la coppia successiva
    Non servirebbe ... Ma "male" non fa se lo gestisci correttamente.
Devi accedere o registrarti per scrivere nel forum
19 risposte