IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

avec Java Discussion :

diner des philosophes


Sujet :

avec Java

  1. #1
    Membre à l'essai
    Femme Profil pro
    Étudiant
    Inscrit en
    Avril 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2012
    Messages : 29
    Points : 16
    Points
    16
    Par défaut diner des philosophes
    Bonjour,
    J'essaie d'implémenter le diner des philosophes en utilisant les moniteurs de java mais seulement deux des 5 philosophes mangent.
    Quelle est mon erreur ?
    Merci !

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
     
    import java.util.concurrent.locks.Condition;
    import java.util.concurrent.locks.Lock;
    import java.util.concurrent.locks.ReentrantLock;
     
    public class Main {
    static int nombreDePhilosophes = 5;
    static int[] etats = new int[nombreDePhilosophes];
     
    	public Main(){
     
    	}
    		public static void main(String[] args) {
    			new Main();
    			for (int i = 0; i < nombreDePhilosophes; i++) {
    				new Thread(new Philo(i)).start();
    			}
    		}
    }
     
    import java.util.concurrent.locks.Condition;
    import java.util.concurrent.locks.Lock;
    import java.util.concurrent.locks.ReentrantLock;
     
     
    public class Philo implements Runnable {
    	int i;
    	Lock lock;
    	Condition[] eat = new Condition[Main.nombreDePhilosophes];
     
    	public Philo(int i) {
    		this.i=i;
    		this.lock = new ReentrantLock();
    		for(int j =0;j<Main.nombreDePhilosophes;j++){
    			this.eat[j] = lock.newCondition();
    		}
    	}
     
    	public void run() {
    		new Philo(i);
    		System.out.println("Le philosophe "+i+" est arrivé");
    		while(true){
    			prendre_une_fourchette(i);
    			poser_fourchette(i);
    		}
    	}
     
    	private void prendre_une_fourchette(int i) {
    		lock.lock();
    		try{
    		while(Main.etats[(i+1)%Main.nombreDePhilosophes]==1 | Main.etats[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes]==1 )
    			try {
    				Main.etats[i]=2;
    				eat[i].await();
    			} catch (InterruptedException e) {
    			}
    		Main.etats[i]=1;//mange		
    		}finally{
    			lock.unlock();
    		}
    		manger();
     
    	}
     
     
    	private void poser_fourchette(int i) {
    		lock.lock();
    		try{
    		if(Main.etats[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes]==2){
    			eat[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes].signal();
    		}
    		if(Main.etats[(i+1)%Main.nombreDePhilosophes]==2 ){
    			eat[(i+1)%Main.nombreDePhilosophes].signal();
    		}
    		Main.etats[i]=0;//ne mange plus		
    		}finally{
    			lock.unlock();
    		}
    		pense();
     
    	}
     
    	private void pense() {
    		System.out.println("Philosophe "+i+" est en train de penser.");
    		long wait=(long)(Math.random()*1000);
    		try {
    			Thread.sleep(wait);
    		} catch (InterruptedException e) {
    		}
    	}
     
    	private void manger() {
    		System.out.println("Philosophe "+i+" est en train de manger");
    		long wait=(long)(Math.random()*1000);
    		try {
    			Thread.sleep(wait);
    		} catch (InterruptedException e) {
    		}
    	}
    }

  2. #2
    Expert éminent sénior
    Avatar de tchize_
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2007
    Messages
    25 481
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : Belgique

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 481
    Points : 48 806
    Points
    48 806
    Par défaut
    Je n'ai pas regardé en détail, mais t'as un gros soucis avec the verrous, ils sont spécifiques à chaque thread, alors que la logique voudrait que les verrous soient globaux. Du coup ton tableau d'état n'est pas protégé, ce qui risque d'amener la création ou la disparition d'une fourchette.

  3. #3
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Janvier 2010
    Messages
    312
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2010
    Messages : 312
    Points : 533
    Points
    533
    Par défaut
    Bonjour,

    Le soucis semble venir du fait que tu crées un tableau de conditions par philo et un lock différent par philo.

    tu changes le eat[i-1] d'un autre philo mais ce dernier ne connait pas la variable eat[] de l'autre philo. Il faut que ce soit commun.

    JE m'embrouille.......

    Regarde si ça répond à ton problème :

    Main

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
     
    import java.util.concurrent.locks.Condition;
    import java.util.concurrent.locks.Lock;
    import java.util.concurrent.locks.ReentrantLock;
     
    public class Main {
     
    	static int nombreDePhilosophes = 5;
    	static int[] etats = new int[nombreDePhilosophes];
    	static Lock lock;
    	static Condition[] eat = new Condition[Main.nombreDePhilosophes];
     
    	public Main(){
    		this.lock = new ReentrantLock();
    	}
    	public static void main(String[] args) {
    		new Main();
    		for (int i = 0; i < nombreDePhilosophes; i++) {
    			etats[i]=0;
    			new Thread(new Philo(i)).start();
    		}
    	}
    }

    philo :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
     
    import java.util.concurrent.locks.Condition;
    import java.util.concurrent.locks.Lock;
    import java.util.concurrent.locks.ReentrantLock;
     
     
    public class Philo implements Runnable {
    	int i;
     
    	public Philo(int i) {
    		this.i=i;
    		Main.eat[i] = Main.lock.newCondition();
    	}
     
    	public void run() {
    		System.out.println("Le philosophe "+i+" est arrivé");
    		while(true){
    			prendre_une_fourchette(i);
    			poser_fourchette(i);
    		}
    	}
     
    	private void prendre_une_fourchette(int i) {
    		Main.lock.lock();
    		try{
    			while(Main.etats[(i+1)%Main.nombreDePhilosophes]==1 || Main.etats[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes]==1 )
    				try {
    					Main.etats[i]=2;
    					Main.eat[i].await();
    				} catch (InterruptedException e) {
     
    				}
    			Main.etats[i]=1;//mange		
    		}finally{
    			Main.lock.unlock();
    		}
    		manger();
     
    	}
     
     
    	private void poser_fourchette(int i) {
    		Main.lock.lock();
    		try{
    		if(Main.etats[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes]==2){
    			Main.eat[(i-1+Main.nombreDePhilosophes)%Main.nombreDePhilosophes].signal();
    		}
    		if(Main.etats[(i+1)%Main.nombreDePhilosophes]==2 ){
    			Main.eat[(i+1)%Main.nombreDePhilosophes].signal();
    		}
    		Main.etats[i]=0;//ne mange plus		
    		}finally{
    			Main.lock.unlock();
    		}
    		pense();
     
    	}
     
    	private void pense() {
    		System.out.println("Philosophe "+i+" est en train de penser.");
    		long wait=(long)(Math.random()*5000);
    		try {
    			Thread.sleep(wait);
    		} catch (InterruptedException e) {
    		}
    	}
     
    	private void manger() {
    		System.out.println("Philosophe "+i+" est en train de manger");
    		long wait=(long)(Math.random()*5000);
    		try {
    			Thread.sleep(wait);
    		} catch (InterruptedException e) {
    		}
    	}
    }

  4. #4
    Membre à l'essai
    Femme Profil pro
    Étudiant
    Inscrit en
    Avril 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2012
    Messages : 29
    Points : 16
    Points
    16
    Par défaut Merci pour vos réponses !
    J'avais mal compris l'usage du verrou en effet. J'en avais un pour chaque philosophe, ce qui n'est pas logique.
    Merci beaucoup pour vos réponses !

    Voici la version finale de mon code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    import java.util.concurrent.locks.Condition;
    import java.util.concurrent.locks.Lock;
    import java.util.concurrent.locks.ReentrantLock;
     
    public class Monitor{
    static int nombreDePhilosophes = 5;
    static int[] etats = new int[nombreDePhilosophes];
    static Lock lock = new ReentrantLock();
    static Condition[] eat = new Condition[Monitor.nombreDePhilosophes];
     
    	public Monitor(){
    		for(int j =0;j<nombreDePhilosophes;j++){
    			eat[j] = lock.newCondition();
    		}
    	}
    		public static void main(String[] args) {
    			new Monitor();
    			for (int i = 0; i < nombreDePhilosophes; i++) {
    				etats[i]=0;//everyone starts thinking
    				new Thread(new Philo(i)).start();
    			}
     
    		}
    		static void prendre_une_fourchette(int i) {
    			try {
    				lock.lock();
    				etats[i]=2;//wants to eat
    				if(etats[(i-1+nombreDePhilosophes)%nombreDePhilosophes] !=1 && etats[(i+1+nombreDePhilosophes)%nombreDePhilosophes] !=1){
    					//si les 2 voisins ne mangent pas, je mange
    					System.out.println("Philo "+ i+" a ses 2 fourchettes.");
    					etats[i]=1;
    				}else{
    					try {
    						eat[i].await();
    						System.out.println("Philo "+ i+" a ses 2 fourchettes.");
    						etats[i]=1;//mange	
    					} catch (InterruptedException e) {
    					}
    				}
    				}finally{
    				lock.unlock();
    			}
    			manger(i);
    		}
     
     
    		static void poser_fourchette(int i) {
    			lock.lock();
    			try{
    				etats[i]=0;//ne mange plus	
    			if(etats[(i-2+nombreDePhilosophes)%nombreDePhilosophes] !=1 && etats[(i-1+nombreDePhilosophes)%nombreDePhilosophes]==2){
    				for(int j =0;j<nombreDePhilosophes;j++){
    					System.out.println("Etat Philo "+j+" "+etats[j]);
    				}
    				System.out.println("Philo "+ i +" signale à Philo "+(i-1+nombreDePhilosophes)%nombreDePhilosophes +" que sa fourchette de droite est libre.");
    				eat[(i-1+nombreDePhilosophes)%nombreDePhilosophes].signal();
    			}
    			if(etats[(i+2+nombreDePhilosophes)%nombreDePhilosophes] !=1 && etats[(i+1+nombreDePhilosophes)%nombreDePhilosophes]==2 ){
    				for(int j =0;j<nombreDePhilosophes;j++){
    					System.out.println("Etat Philo "+j+" "+etats[j]);
    				}
    				System.out.println("Philo "+ i +" signale à Philo "+(i+1+nombreDePhilosophes)%nombreDePhilosophes +" que sa fourchette de gauche est libre.");
    				eat[(i+1+nombreDePhilosophes)%nombreDePhilosophes].signal();
    			}
    			}finally{
    				lock.unlock();
    			}
    			pense(i);
     
    		}
     
    		static void pense(int i) {
    			System.out.println("Philosophe "+i+" est en train de penser.");
    			long wait=(long)(Math.random()*1000);
    			try {
    				Thread.sleep(wait);
    			} catch (InterruptedException e) {
    			}
    		}
     
    		static void manger(int i) {
    			System.out.println("Philosophe "+i+" est en train de manger ");
    			long wait=(long)(Math.random()*1000);
    			Monitor.etats[i]=1;
    			try {
    				Thread.sleep(wait);
    			} catch (InterruptedException e) {
    			}
    		}
    	}
    et
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
     
    public class Philo implements Runnable {
    	int i;
     
    	public Philo(int i) {
    		this.i=i;
    	}
     
    	public void run() {
    		new Philo(i);
    		System.out.println("Le philosophe "+i+" est arrivé");
    		while(true){
    			Monitor.prendre_une_fourchette(i);
    			Monitor.poser_fourchette(i);
     
    		}
    	}
    }

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 2
    Dernier message: 10/03/2014, 17h00
  2. probleme des philosophes en java
    Par esthr dans le forum Général Java
    Réponses: 5
    Dernier message: 07/06/2008, 22h24
  3. probleme des philosophes en C
    Par esthr dans le forum C
    Réponses: 6
    Dernier message: 04/10/2007, 17h51
  4. probleme des philosophes en c++
    Par esthr dans le forum C++
    Réponses: 2
    Dernier message: 04/10/2007, 16h13
  5. recherches des cours ou des explications sur les algorithmes
    Par Marcus2211 dans le forum Algorithmes et structures de données
    Réponses: 6
    Dernier message: 19/05/2002, 22h18

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo