2010-09-06 30 views

Trả lời

23

không, một lớp không thể có hàm tạo ảo.

Không có ý nghĩa khi có một hàm tạo ảo. Thứ tự trong đó các đối tượng được xây dựng trong C# là bằng cách xây dựng các lớp dẫn xuất đầu tiên, do đó, hàm khởi tạo có nguồn gốc luôn được gọi vì lớp bạn muốn gọi cũng được biết đến tại thời điểm xây dựng.

Một điều khác là, nếu bạn thực sự gõ mã này ra, bạn có thể nhanh chóng thấy rằng nó làm cho cảm giác rất ít ở tất cả

Nếu bạn có:

public class BaseClass 
{ 
    public virtual BaseClass() 
    { 
    } 
} 

và sau đó

public class InheritedClass : BaseClass 
{ 
    //overrides baseclass constructor but why would you do this given that the  
    //constructor is always going to be called anyway?? 
    public override InheritedClass() 
    { 
    } 
} 
+1

Liên quan đến việc gọi hàm tạo cơ sở trong lớp dẫn xuất: sẽ không có một chuỗi căn cứ như bình thường, ví dụ: 'Ghi đè công khai InheritedClass(): base()'. –

+0

@paul ruane: bạn đúng, nhưng điểm tôi cố gắng thực hiện là việc ghi đè lớp cơ sở là thừa vì bạn sẽ rõ ràng về nó và tham khảo nó bằng cách sử dụng base() hoặc bạn không nó sẽ được gọi khi đối tượng được xây dựng, do đó, việc có một hàm tạo ảo là vô nghĩa – lomaxx

+8

Nó có ý nghĩa hoàn hảo để có các hàm tạo ảo. Đây là những gì các mẫu trình xây dựng khác nhau đạt được bằng các ngôn ngữ không hỗ trợ trực tiếp. –

0

Tuyên bố điều gì đó ảo nghĩa là nó có thể bị ghi đè bởi một lớp con của lớp hiện tại. Tuy nhiên hàm tạo được gọi khi một lớp được khởi tạo. Tại thời điểm đó bạn không thể tạo một lớp con của lớp đang được đề cập đến vì vậy sẽ không bao giờ cần phải khai báo một hàm tạo ảo.

5

Không trực tiếp, nhưng phương pháp nhà máy mẫu Gang of Four cổ điển đạt được số tiền sẽ tạo cho một nhà xây dựng ảo của các loại, bằng cách trì hoãn việc khởi tạo cho các lớp con.

2

Không, nó hoạt động như thế nào? Tất cả các nhà xây dựng trong hệ thống phân cấp phải được gọi khi bạn lấy được các lớp con từ các lớp cơ sở. Tạo một hàm tạo ảo sẽ ngụ ý ngược lại.

Thứ gì đó có thể được mô tả là có hàm tạo ảo như hành vi, là khi bạn sử dụng mẫu nhà máy. Hãy tưởng tượng kịch bản này:

class AnimalFactory 
{ 
    virtual Animal CreateAnimal(return new Animal("Cow");); 
} 

Hành vi mặc định của nhà máy này là tạo bò. Nhưng nếu chúng tôi tạo lớp học có nguồn gốc:

class DogFactory : AnimnalFactory 
{ 
    override Animal CreateAnimal(return new Animal("Dog");); 
} 

Chúng tôi hiện đang tạo chó. Tất nhiên đây không phải là một nhà xây dựng ảo thực sự (điều đó là không thể), đây là xây dựng ảo.

1

Nếu chúng ta nhìn vào các định nghĩa của hàm tạo từ và ảo, chúng ta đã đi đến một kết luận hợp lý rằng một hàm tạo không thể là ảo.

+3

Thật sao? Trong Delphi, các nhà xây dựng ảo là một sự xuất hiện phổ biến để đi cùng với các LOẠI LẠNH CLASS ("CLASS OF "). Một khái niệm mà C-lập trình viên không có kiến ​​thức :-). Có - Tôi biết câu hỏi nói C#, nhưng khái niệm về các nhà xây dựng ảo không phải là mâu thuẫn về mặt ngôn ngữ :-). – HeartWare

+0

Bạn có quyền, về các nhà xây dựng ảo trong Delphi nhưng, hậu quả này từ đặc tả ngôn ngữ. Bạn khai báo một phương thức và trạng thái này sẽ là một hàm tạo. Tên phương thức không liên quan đến kiểu tạo ra cái gì. Và đây là chìa khóa để hiểu tại sao khái niệm chung của constructor ảo là không hợp lệ. Bạn có thể khai báo một phương thức nhà máy và thậm chí ghi đè nó. Vì vậy, cách được quay lại Delphi có phương pháp ảo có thể được đặt tên là các nhà xây dựng nhưng nó không có cấu trúc mà nó là một nhà xây dựng của chính nó giống như các ngôn ngữ khác của C không. –

11

Phương pháp ảo theo định nghĩa phương thức được gửi dựa trên phân tích kiểu thời gian chạy của người nhận, không phải là phân tích kiểu tĩnh thời gian biên dịch của người nhận.

Một hàm tạo là một phương thức được gọi khi một cá thể mới của một kiểu cụ thể được tạo ra.

Vì kiểu thời gian chạy của đối tượng mới được tạo là luôn cùng kiểu (*), không cần các nhà xây dựng ảo: công văn thời gian sẽ luôn chọn phương thức tương tự như công văn tĩnh , vậy tại sao lại tạo ra sự khác biệt?

(*) Điều này không hoàn toàn đúng; có các kịch bản liên quan đến COM interop trong đó kiểu thời gian chạy của một công trình không phải là kiểu thời gian biên dịch.Nhiều điều kỳ lạ trong thế giới của mã interop cũ.

1

Just FYI khi người ta đang yêu cầu cho nhà xây dựng một mô hình ảo rất tốt để nhìn vào là InversionOfControl

Trong .NET, chúng tôi có một vài container IoC như ObjectBuilder, Unity, MEF, Spring.NET. Trong Java (có nguy cơ thể hiện sự thiếu năng lực Java của tôi) có Spring, Tapestry và nhiều thứ khác.

IMHO IoC là những gì làm cho OO mang lại lời hứa của mình.

Các vấn đề liên quan