Вопрос

У меня есть три класса (класс A, класс B и класс C).

Класс A вызывает экземпляр B и запускает start().

Класс B расширяет поток, поэтому при вызове start() выполняется все, что содержится в методе run().

В потоке run() есть экземпляр класса C.

Можно ли в любом случае разрешить методу в классе C вызывать метод в классе A без создания нового экземпляра класса A?

Поскольку я не могу расширить класс A до класса B (потому что "Поток" уже расширен), я не знаю, как бы я это сделал.

Извините за расплывчатость, но мой проект содержит слишком много кода и слишком сложен, чтобы привести прямой пример кода.

Спасибо!

Это было полезно?

Решение

Итак, у вас есть

class A {
 void run()
 {
  new B().start();
 }
}

class B extends Thread {
  public void run(){
    C c = new C();  
    c.do something with A .. }
}

Вы можете передать вызывающего абонента, что может стать некрасивым, так как вам нужно передать A вплоть до C через B:

class A {
 void run()
 {
  new B(this).start();
 }
}

class B extends Thread {
  public void run(A a){ 
    C c = new C();
    c.do something(a).. 
  }
}

или упростить, особенно если у B и C нет другой причины для:

class A {
 public void run()
 {
   this.do something() ... 
 }
}

Другие советы

это циклическая зависимость, по моему (скромному) мнению, очень плохая вещь в ООП.

Вы должны провести рефакторинг своего кода, чтобы предоставить общий класс для A и C.

Лучшим способом может быть, чтобы класс B начал перегружаться, чтобы принять параметр (A или, еще лучше, интерфейс, реализованный A).Затем B может либо сохранить это для извлечения C (если это внутренний класс), либо передать его конструктору C...

Редактировать:

Хотя, как упомянул комментатор, переопределение конструктора сработало бы, это не соответствует параметрам вопроса, который был сформулирован таким образом, что B уже существовал, поэтому мое предложение состоит в том, чтобы перегрузить start() следующим образом:

b.start(A aParam) {
    a=aParam;
    start();
}

Однако эта версия НЕ является потокобезопасной.Конструктор B работает, если экземпляр B фактически создается каждый раз, или если экземпляр C создается при запуске b, тогда он может быть передан конструктору C по мере создания экземпляра.

Кстати, расширение потока, как правило, не так хорошо, как реализация runnable по целому ряду причин.

Другой способ использовать поведение потока в java - это реализовать Runnable.Предположительно, вы могли бы расширить A, и реализовать Runnable, и использовать:

Thread t = new Thread( b )
t.start();

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

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top