Модераторы: LSD, AntonSaburov

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Неправильно работаю с потоками, вылазиет ошибка,направьте в нужное русло 
:(
    Опции темы
barin_Student
Дата 7.11.2007, 06:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Собсвенно так можно поставить вопрос: есть поток демон , он работает постоянно , то есть while (true)  в методе run выполняются действия некоторые. В какой то момент мне нужно остановить или удалить этот поток. Делаю так 
t- это поток.
t.stop();- нормально проходит, но пишет на isAlive() - false , isDaemon - true, в этом странность №1.
t.destroy() - IllegalMonitorException, на java.sun по этой ошибке вот что сказанно :Thrown to indicate that a thread has attempted to wait on an object's monitor or to notify other threads waiting on an object's monitor without owning the specified monitor. Так что мне синхронизация нужна? И почему он не может просто умереть? Помогите кто знает точно мз за чего чаще всего вылазиет эта ошибка. 




--------------------
Нехорошо блин!!!
PM MAIL   Вверх
mbasil
Дата 7.11.2007, 09:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 399
Регистрация: 4.5.2007
Где: Москва

Репутация: 2
Всего: 13



Похоже, что загадок никаких и нет.
1. Вы вызываете устаревший метод stop() и поток "умирает".
2. Это приводит к возврату  isAlive() - false, что нормально, так как поток мертв.
3. isDaemon - true потому, что он БЫЛ демон
4. Затем Вы вызываете на МЕРТВОМ потоке устаревший метод destroy(),
    который и вовсе:
  "Deprecated. This method was originally designed to destroy this thread without any cleanup. Any    monitors it held would have remained locked. However, the method was never implemented. If if were to be implemented, it would be deadlock-prone in much the manner of suspend(). If the target thread held a lock protecting a critical system resource when it was destroyed, no thread could ever access this resource again. If another thread ever attempted to lock this resource, deadlock would result. Such deadlocks typically manifest themselves as "frozen" processes." 

Остается один вопрос - зачем Вы после остановки потока с помощью Deprecated метода stop()
пытаетесь вызвать на мертвом потоке еще и  безобразный и Deprecated метод destroy()

Добавлено @ 10:03
Используйте флаг для проверки цикла, ане просто true.
Вызывайте для остановки потока interrupt() изменив при перехвате исключения
значение флага с true на false. 


Это сообщение отредактировал(а) mbasil - 7.11.2007, 10:03
PM MAIL   Вверх
barin_Student
Дата 7.11.2007, 11:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Собственно , мне надо демона Стопать  и запускать скажем тот же поток. Сейчас я его не убиваю Дестоем ,а стопаю , потом опять старт - и не работает , ладно еще поэкспериментирую и ответ с примером выложу.


--------------------
Нехорошо блин!!!
PM MAIL   Вверх
w1nd
Дата 7.11.2007, 11:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Вертилятор
***


Профиль
Группа: Завсегдатай
Сообщений: 1077
Регистрация: 22.3.2006
Где: Москва

Репутация: 20
Всего: 54



Цитата(barin_Student @  7.11.2007,  11:27 Найти цитируемый пост)
Сейчас я его не убиваю Дестоем ,а стопаю , потом опять старт - и не работает , ладно еще поэкспериментирую и ответ с примером выложу.

Так не получится. Для того, чтобы иметь возможность возобновить выполнение потока, его не следует останавливать.


--------------------
user posted imageuser posted image
PM MAIL ICQ   Вверх
mbasil
Дата 7.11.2007, 12:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 399
Регистрация: 4.5.2007
Где: Москва

Репутация: 2
Всего: 13



Надо поток не убивать, а усыплять и потом пробуждать вновь, при необходимости.
И не используйте Deprecated методы. Разработчики Java не зря объявили эти методы
устаревшими -  в этом случае они приняли совершенно правильное решение.

Добавлено @ 12:17
Если точнее - "убитый" поток нельзя запустить вновь !
А вызов stop() приводит к страшной и мучительной смерти потока, а вовсе не его остановке, как Вы думаете.

Это сообщение отредактировал(а) mbasil - 7.11.2007, 12:20
PM MAIL   Вверх
barin_Student
Дата 7.11.2007, 12:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Лано ,а как мне сделать усыпление на неопределенное время , и разбудить когда захочется? smile 


--------------------
Нехорошо блин!!!
PM MAIL   Вверх
Platon
Дата 7.11.2007, 12:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1801
Регистрация: 25.4.2006

Репутация: 16
Всего: 40



Странно, что никто еще не направил на FAQ
PM MAIL ICQ   Вверх
mbasil
Дата 7.11.2007, 12:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 399
Регистрация: 4.5.2007
Где: Москва

Репутация: 2
Всего: 13



Код

 public class Runner implements Runnable {

 private boolean timeToQuit=false;
 private boolean flagWait=false;

 public void run() {
   synchronized( this ) {
     while ( ! timeToQuit ) {
        System.out.print( "." );
        if( flagWait ) {
          try {
                System.out.println("W" );
                wait();
           } catch (InterruptedException e) {
                flagWait=false;
                System.out.println("!!!! InterruptedException !!!" );
             // ...
          }
        }
              // . . . 
       try {
             Thread.sleep( 10 );
       } catch ( InterruptedException e ) {}
      }
    }
        // clean up before run() ends
 }

 public void stopRunning() {
   timeToQuit = true;
 }
 
 public void setFlagWait( boolean flag ) {
   flagWait = flag;
 }

 public static void main( String args[] ) {
  Runner r = new  Runner();
  Thread t = new Thread(r);
  t.setDaemon( true );
  t.start();
     r.setFlagWait( true );
     try {
             Thread.sleep( 2000 );
       } catch ( InterruptedException e ) {}
     t.interrupt();
     try {
             Thread.sleep( 2000 );
       } catch ( InterruptedException e ) {}
 }
}

PM MAIL   Вверх
barin_Student
Дата 7.11.2007, 12:58 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Да там о синхронизации все сказанно , а не о приастановке и старте. Интересно если у вас машина на трассе сломается , вы заедите на стоянку Камазистов и вам скажут вот книга читайте . - во всех случаях проблемы банальные не знают FAQ , просто есть сложнее и проще. Но вы ведь ответ знаете , почему просто не помочь , я ведь все таки учусь. smile 


--------------------
Нехорошо блин!!!
PM MAIL   Вверх
Platon
Дата 7.11.2007, 13:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1801
Регистрация: 25.4.2006

Репутация: 16
Всего: 40



Также надо учиться добывать информацию и весь мир не только вокруг тебя вертится, чтоб подгонять христоматийные выдержки. В Факе это дело расписано.
Но вот элементарное описание
Есть у класса Object 4 интересных метода по работе с потоками
wait() - ждет неизмеримо бесконечно, пока его не разбудят
notify() - уведомляет (будит) 1 из потоков в стопке ожидающих потоков
notifyAll() - уведомляет (будит) всех ждущих потоков
join() - ждет завершения работы потока

остальное в любом поиске.

Добавлено через 5 минут и 4 секунды
Насчет "вращения", ничего личного, просто это базовый вопрос, его лучше изучить по книге, а не хвататься за то, что тебе на форуме скинут.
Более того, о машине. Как говорится, "на переправе коней не меняют", если у тебя такая задача стоит, тебе необходимо изучить предметную область, и более того, технологии, средством которых ты будешь достигать цели.
PM MAIL ICQ   Вверх
barin_Student
Дата 7.11.2007, 14:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Значит я делаю так
t- поток(демон)
t.wait();
Потом какие то действия и вызываю метод notify(), но wait не работает , почему?
Поток вот как примерно выглядит:
Код

public class t extends Thread{
   public void g()
  {
      //bla bla
   }
public void run()
{
    while(true)
    {
       this.g();
     }
}
}



--------------------
Нехорошо блин!!!
PM MAIL   Вверх
Platon
Дата 7.11.2007, 14:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1801
Регистрация: 25.4.2006

Репутация: 16
Всего: 40



А где у тебя тут wait()?

Код

public class t extends Thread{
   synchronized public void g()
  {
      //bla bla
      try {
      wait();
      } catch(Exception e) {}
   }
public void run()
{
    while(true)
    {
       this.g();
     }
}

synchronized public wakeIt() {
    notify();
}

PM MAIL ICQ   Вверх
barin_Student
Дата 7.11.2007, 14:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



А разве wait(), тоже надо в теле класса t описывать?
Код

t.setDaemon(true);
t.start();
t.wait();// IlliegalMonitorException
t.notyfy();


Добавлено через 12 минут и 21 секунду
Сделал так тоже самое:
Код

public class t extends Thread
{
    public void Waiter()
   {
          try
          {
                this.wait();
           }
           catch(Exception e)
          {
           }
   }
  public void starter()
  {
          this.notify();
   }
}

Вызываю  так
t thread = new t();
t.start();
t.Waiter();// там в catch и выводит IllegalMonitorException;


--------------------
Нехорошо блин!!!
PM MAIL   Вверх
mbasil
Дата 7.11.2007, 20:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 399
Регистрация: 4.5.2007
Где: Москва

Репутация: 2
Всего: 13



wait() можно вызывать только в синхронизированном коде.
Я же Вам привел  пример приостанавливаемого потока-демона.
Еще раз с комментариями и небольшими улучшениями
Код

 public class Runner implements Runnable {

 private boolean timeToQuit=false;
 private boolean flagWait=false;

 public void run() {
   synchronized( this ) {
     while ( ! timeToQuit ) {
        System.out.print( "." );
        if( flagWait ) {
          try {
                System.out.println("W" );
                wait();
           } catch (InterruptedException e) {
                flagWait=false;
                System.out.println("!!!! InterruptedException !!!" );
             // . . .
          }
        }
              // . . . 
       try {
             Thread.sleep( 10 );
       } catch ( InterruptedException e ) {}
      }
    }
      System.out.println("\n!!!! Thread Daemon STOP !!!" );
        // clean up before run() ends
 }

 public void stopRunning() {
   timeToQuit = true;
 }
 
 public void setFlagWait( boolean flag ) {
   flagWait = flag;
 }

 public static void main( String args[] ) {
  Runner r = new Runner();
  Thread t = new Thread( r );
  t.setDaemon( true );   //  Делаем поток демоном
  t.start();            // Стартуем поток
     r.setFlagWait( true );  // Переводим поток в состояние 
                            // бесконечного ожидания
     try {      // Усыпляем главный поток на 2 секунды
             Thread.sleep( 2000 );
       } catch ( InterruptedException e ) {}
     r.setFlagWait( false );  // устанавливаем флаг 
    synchronized( r ) {  
       r.notify();        //  Будим поток
     }
   //  t.interrupt();  //  Если потоков много, то адресно
     try {
             Thread.sleep( 2000 );
       } catch ( InterruptedException e ) {}
     // Здесь завершается жизнь главного потока и
    // автоматически потока-демона. Если Вы все-же хотите 
   // остановить поток-демон явно, вызовите 
          r.stopRunning();
 }
}

PM MAIL   Вверх
barin_Student
Дата 8.11.2007, 06:20 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 488
Регистрация: 10.8.2007
Где: Казахстан , Алмат ы

Репутация: 1
Всего: 2



Ok ? счас попробую , теперь что то стало понятно. smile 


--------------------
Нехорошо блин!!!
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Java"
LSD   AntonSaburov
powerOn   tux
javastic
  • Прежде, чем задать вопрос, прочтите это!
  • Книги по Java собираются здесь.
  • Документация и ресурсы по Java находятся здесь.
  • Используйте теги [code=java][/code] для подсветки кода. Используйтe чекбокс "транслит", если у Вас нет русских шрифтов.
  • Помечайте свой вопрос как решённый, если на него получен ответ. Ссылка "Пометить как решённый" находится над первым постом.
  • Действия модераторов можно обсудить здесь.
  • FAQ раздела лежит здесь.

Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, LSD, AntonSaburov, powerOn, tux, javastic.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Java: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1100 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.