Hãy nói rằng tôi có một lớp JavaChạy một phương pháp sau các nhà xây dựng của bất kỳ lớp được thừa kế
abstract class Base {
abstract void init();
...
}
và tôi biết mỗi lớp được thừa kế sẽ phải gọi init()
sau khi nó được xây dựng. Tôi có thể, tất nhiên, chỉ cần gọi nó trong nhà xây dựng các lớp học có nguồn gốc:
class Derived1 extends Base {
Derived1() {
...
init();
}
}
class Derived2 extends Base {
Derived2() {
...
init();
}
}
nhưng điều này phá vỡ 'không lặp lại chính mình' nguyên tắc chứ không phải xấu (và có sẽ có nhiều lớp con của Base
). Tất nhiên, các cuộc gọi init()
không thể đi vào các nhà xây dựng Base()
, vì nó sẽ được thực hiện quá sớm.
Bất kỳ ý tưởng nào về cách vượt qua vấn đề này? Tôi cũng rất vui khi thấy giải pháp Scala.
UPDATE: Đây là một phiên bản generic của cách tiếp cận Factory Method:
interface Maker<T extends Base> {
T make();
}
class Base {
...
static <T extends Base> T makeAndInit(Maker<T> maker) {
T result = maker.make();
result.init();
return result;
}
}
UPDATE 2: Câu hỏi này về cơ bản là "làm thế nào để bạn sử dụng Template Method cho nhà xây dựng"? Và câu trả lời có vẻ là, "Bạn có thể, nhưng đó là một ý tưởng tồi". Vì vậy, tôi có thể làm một nhà máy mẫu (Template Method + Abstract Factory) để thay thế.
Nếu init() là trừu tượng trong lớp cơ sở, thì tại sao mọi lớp dẫn xuất phải gọi nó? Điều gì sẽ xảy ra nếu họ không? –
Tại sao bạn không gọi init() trong hàm tạo của lớp 'Base'? – aioobe
@Skip Head: chúng sẽ không được khởi tạo đúng cách. –