0

ここでちょっとした問題に遭遇しました。Javaで並行プログラムを実行しています。問題: 4 人 (学生) がプリンターにアクセスして、5 つのドキュメントを印刷しようとしています。ただし、一度に印刷できるのは 1 つだけです (明らかなように) 5 つのドキュメント。終了すると、他のスレッドが完了したことを通知し、他のスレッドがリソースにアクセスします。メインクラス、学生クラス、モニター(レーザープリンター)、(ページ数、名前ユーザーIDなど)+プリンター用のいくつかのインターフェイスなどのドキュメントに関する情報を保持するドキュメントクラスがあります。スレッドを正常に実行できましたが、それらは同期されていません (相互排除)
問題は、相互排除を達成する方法です (一度に 1 人だけが自分のドキュメント数を印刷できるということです)
ご覧いただきありがとうございます。時間とヒント: )

メインクラス

    String S1Name = "bob";
    String S2Name = "klara";
    String S3Name = "John";
    String S4Name = "Iga";

    String T1Name = "Man";
    String T2Name = "Woman";


    final int NoOfDocs = 5;
    ServicePrinter sp = new LaserPrinter();

    ThreadGroup groupA = new ThreadGroup("Group A"); 
    ThreadGroup groupB = new ThreadGroup("Group B");

    Student student1 = new Student(sp,NoOfDocs,S1Name, groupA);
    Student student2 = new Student(sp,NoOfDocs,S2Name, groupA);
    Student student3 = new Student(sp,NoOfDocs,S3Name, groupA);
    Student student4 = new Student(sp,NoOfDocs,S4Name, groupA);

    TonerTechnician TT = new TonerTechnician(groupB);
    PaperTechnician PT = new PaperTechnician(groupB);

    /*
     * Start Student Threads
     */
    student1.start();
    student2.start();
    student3.start();
    student4.start();

    /*
     * Start Technician threads
     */
    TT.start();
    PT.start();

学生クラス

 private final ServicePrinter serviceprinter;
    private final int NoOfDocs;
    private final String Name;
    private final ThreadGroup threadgroup;

    public Student(ServicePrinter serviceprinter, int NoOfDocs, String Name, ThreadGroup threadgroup)
    {
        this.serviceprinter = serviceprinter;
        this.NoOfDocs = NoOfDocs; 
        this.Name = Name;
        this.threadgroup = threadgroup;
    }
    @Override
    public void run()
    {
        /*
         * each students prints 5 documents (different name and length)
         */
        final LaserPrinter lp = new LaserPrinter();
        //sleep from 1 to 5 sec random time
        final Random random = new Random();       
        char[] chars = "abcdefghijklmnopqrstuvwxyz".toCharArray();
        StringBuilder sb = new StringBuilder();
        /*
         * Create random document name 10 characters long
         */
        for (int i = 0; i < 10; i++) 
        {
            char c = chars[random.nextInt(chars.length)];
            sb.append(c);
        }
        String docName  = sb.toString();
        /*
         * print 5 documents (random sleep time between printing)
         */
        for(int i = 0; i < NoOfDocs; i++)
        {
            try 
            {
                Document coursework = new Document(Name,docName,random.nextInt(90)+10);
                lp.printDocument(coursework);
                Thread.sleep(random.nextInt(1000)+4000);                
            } 
            catch (InterruptedException ex) 
            {
                Logger.getLogger(Student.class.getName()).log(Level.SEVERE, null, ex);
            }            
        }
        System.out.println("User: " + Name+ " completed printing");

モニタークラス

    int tonerLevel = 500;
    int paperLevel = 250;

    private final String PrinterName = "HP";
    private final String PrinterID = "LX-440";
    private int CurrentPaperLevel;
    private int CurrentTonerLevel;
    private int NoOfDocsPrinted;

    @Override
    public synchronized void printDocument(Document document) {
        System.out.println(document);

    }
4

2 に答える 2

0

Studentクラスに渡す共有オブジェクトを使用する代わりに、runメソッドでローカルプリンターオブジェクトを作成しているようです。渡した共有プリンターを使用して、何が得られるかを確認してください。また、でどのように使用するかを確認する必要がありprintDocumentますServicePrinter。これは、クラスでServicePrinterオブジェクトを使用していて、 inの実装が正しくない可能性があるためです(つまり、実際にスーパークラスに実装されている場合)。StudentprintDocumentServicePrinter

于 2013-03-19T19:08:24.477 に答える
0

これは単純なミューテックスの実装ですが、同期にはjava.util.concurrentパッケージを使用する必要があります

編集:ミューテックスをセマフォに変更しました(より理にかなっています)

単純なミューテックスの実装:

public class Mutex {

    private int semaphore;

    public synchronized void aquire() throws InterruptedException {

        if(semaphore < 0) {
            wait();
        }

        semaphore--;

    }

    public synchronized void release() {

        if(semaphore < 0) {
            semaphore++;
            notify();            
        }
    }
}
于 2013-03-19T19:07:13.097 に答える