2010-12-14 7 views
0

Я написал код для реализации проблемы «Продюсер-Потребитель», и, похоже, он работает нормально, без необходимости синхронизации. Возможно ли это?производитель-потребитель, использующий синхронизацию

Как проверить код и проверить, действительно ли он работает правильно или нет? Как узнать, произойдет ли взаимоблокировка? Прямо сейчас я не выхожу из циклов (т. Е. Продюсер продолжает вставлять, а потребитель продолжает потреблять в бесконечном цикле). Я использую круговую очередь размером 3 (для простоты) в качестве общего ресурса.

Вот мой код:

import java.util.*; 

public class PCImpl implements Runnable 
{ 
Thread t; 
QforPC qObj; 

public static void main(String[] args) 
{ 
    QforPC qObject=new QforPC(); 

    //These create 2 different objects! Each object has it's own thread of execution. 
    //Synchronization is needed when 2 threads use the same object 
    new PCImpl("Producer",qObject); 
    new PCImpl("Consumer",qObject); 
} 

PCImpl(String name,QforPC qObj) 
{ 
    this.qObj=qObj; 
    t=new Thread(this,name); 
    t.start(); 
} 

public void run() 
{ 
     if(Thread.currentThread().getName().equals("Producer")) 
     { 
      while(true) 
      { 
        Random rgen=new Random(); 
        int n=rgen.nextInt(100); 
        if(n!=0) 
           qObj.Producer(n); 
         try 
        { 
         Thread.sleep(200); 
        } 
         catch(InterruptedException e) 
        { 

        } 
       } 

      } 


     if(Thread.currentThread().getName().equals("Consumer")) 
     { 
      while(true) 
        { 
       try 
       { 
       Thread.sleep(1500); 
       } 
       catch(InterruptedException e) 
       { 
        } 
       qObj.Consumer(); 

       } 
     } 

    } 
} 



public class QforPC 
{ 
int[] q={0,0,0}; 
int r=0,f=0; 
    public void Producer(int item) 
    { 

     if(r!=q.length && canProducer()) 
     { 
      q[r]=item; 
      System.out.println("The item inserted into the queue is:"+ item); 
      r++; 
     } 
     if(r==q.length && f>0) 
      r=0; 
     else if(r==q.length && f==q.length) 
     { 
      r=0; 
      f=0; 
     } 
    } 

    public void Consumer() 
    { 
     int item; 
     System.out.println("The value of isQueue empty is:"+ isEmpty()); 

     if(f!=q.length && isEmpty()==false) 
     { 
      System.out.println("Entered the consumer method"); 
      item=q[f]; 
      System.out.println("The item fetched from the queue is:"+item); 
      q[f]=0; 
      f++; 
     } 
     if(f==q.length && r<f) 
      f=0; 

    } 

    public boolean isEmpty() 
    { 
     for(int k=0;k<q.length;k++) 
     { 
      if(q[k]==0 && k==q.length-1) 
       return true; 

     } 
     return false; 
    } 

    public boolean canProducer() 
    { 
     for(int k=0;k<q.length;k++) 
     { 
       if(q[k]==0) 
       return true; 

     } 
     return false; 
    } 
} 
+1

Это, вероятно, беспорядок, если вы удалите 'Sleeps'. – SwDevMan81

+2

Добро пожаловать в характер ошибок времени. Кажется, он работает нормально вплоть до момента, когда он полностью взрывается. –

+2

Почему бы не разделить логику производителя и потребителя на две отдельные реализации «Runnable»? Этот дизайн очень неликвиден и приведет к совершенно непримиримому коду. –

ответ

1

Что вы пытались сделать, это реализовать синхронизацию, используя ожидание. В псевдокоде, что вы в основном делаете:

Producer() 
{ 
    if (buffer.hasemptyspaces()) 
    { 
     produce(buffer); 
    } 
    else 
    { 
     sleep(n); 
    } 
} 

Consumer() 
{ 
    if (buffer.hasfullspaces()) 
    { 
     consume(buffer); 
    } 
    else 
    { 
     sleep(n); 
    } 
} 

Вы код будет работать нормально, до производителя и потребителя одновременно пытаются выполнить продукт() и потреблять(). Другими словами, либо одно из Это может быть не очень часто, но, безусловно, возможно и обязательно произойдет!

В Java ConcurrentLinkedQueue реализует алгоритм ожидания для общего буфера. Я уверен, что это другие реализации, если вы посмотрите вокруг.

+0

Итак, это означает, что он не может работать без синхронизации в моей реализации, и в какой-то момент программа выйдет из строя? – collegian

+1

Да. При реализации потоков и общих данных полезно подумать: «Если есть способ чередовать потоки таким образом, что они будут сбой, планировщик найдет его». –

0

Там нет такого понятия, как the Producer-Consumer problem. Продюсер-Потребитель - это шаблон проектирования, который может или не может быть эффективной реализацией решения проблемы, а не само по себе.

Я уверен, что существует множество реализаций-производителей-потребителей, которые не требуют синхронизации. Это полностью зависит от того, что вы пытаетесь выполнить, и каких данных вы производите/потребляете.

Кроме того, у вас должна быть проблема для решения, если вы хотите сказать, что выполняете выполнение без синхронизации. Работает над чем? Я понятия не имею, что вы делаете.

+0

Я просто пытаюсь произвести и затем потреблять! – collegian

+0

Смешно, статья Википедии о проблеме «Продюсер-потребитель», похоже, не согласна. –

+0

Похоже, мое определение проблемы не то же самое, что и у них. Наверное, поэтому я инженер, а не компьютерный ученый. – Falmarri

0

Это можно сделать с помощью бесплатной очереди, но не так, я рекомендую вам прочитать Java Concurrency in Practice. Если ваш код имеет доступ несколькими потоками одновременно, у вас будет много эррос на этом, у вас проблемы с публикацией и синхронизацией! Но, как сказал Фарлмарри, это зависит от использования этого кода.

0

Вы на самом деле не решаете проблему с производителем/потребителем, а просто гуляете по нему :) Ваш код работает из-за времени и из-за того, что если один из двух потоков не смог выполнить загрузку/получение ресурса, он запрашивает его в основном спит на время и пытается снова. Хотя этот worn (когда вам не нужно немедленно обрабатывать событие), он тратит процессорное время.

Поэтому семафоры настоятельно советуем обратиться такого рода вопрос, как вы можете прочитать здесь

http://en.wikipedia.org/wiki/Producer-consumer_problem

свиданья

+0

На самом деле, похоже, что реализация OP очень похожа на реализацию, указанную в этой статье, как «неадекватная». –

 Смежные вопросы

  • Нет связанных вопросов^_^