2012-11-15 27 views
6

sự khác biệt giữa hai trường hợp dưới đây là gì:Sự khác nhau về cách thức các đối tượng này được khởi tạo là gì?

class Data 
{ 
    PersonDataContext persons = new PersonDataContext(); 
    public Data() {} 
} 

so

class Data 
{ 
    PersonDataContext persons; 
    public Data() 
    { 
     persons = new PersonDataContext(); 
    } 
} 

Tôi có cùng một câu hỏi trong asp.net:

public partial class Data : System.Web.UI.Page 
{ 
    PersonDataContext persons = new PersonDataContext(); 
    protected void Page_Load(object sender, EventArgs e) 
    { 
    } 
} 

so

public partial class Data : System.Web.UI.Page 
{ 
    PersonDataContext persons; 
    protected void Page_Load(object sender, EventArgs e) 
    { 
     persons = new PersonDataContext(); 
    } 
} 

Trả lời

3

Trình khởi chạy trường chạy trước lệnh gọi hàm dựng. Vì vậy, trong trường hợp 1 đối tượng của bạn là PersonDataContext sẽ được tạo trước cuộc gọi hàm tạo.

PersonDataContext persons = new PersonDataContext(); 

Trong trường hợp thứ 2, nhà xây dựng của bạn sẽ thực hiện đầu tiên và sau đó nó sẽ khởi tạo lĩnh vực này.

Bạn có thể làm một bài kiểm tra đơn giản

class PersonDataContext 
{ 
    public PersonDataContext() 
    { 
     Console.WriteLine("In PersonDataContext Constructor"); 
    } 
} 
class Data 
{ 
    PersonDataContext persons = new PersonDataContext(); 
    public Data() 
    { 
     Console.WriteLine("In Data Contructor"); 
    } 
} 

class Data2 
{ 
    PersonDataContext persons; 
    public Data2() 
    { 
     Console.WriteLine("In Data2 Constructor"); 
     persons = new PersonDataContext(); 
    } 
} 

và sau đó trong phương thức Main của bạn

static void Main(string[] args) 
{ 

    Data d1 = new Data(); 
    Data2 d2 = new Data2(); 
    Console.Read(); 
} 

Output

Trong PersonDataContext Constructor // Trường hợp 1

Trong dữ liệu Contructor // Case 1

Trong Data2 Constructor // Trường hợp 2

Trong PersonDataContext Constructor // Trường hợp 2


Đối với ví dụ asp, Trong trường hợp đầu tiên Dòng của bạn được khởi tạo trước khi sự kiện Page_Load, và trong Trường hợp 2 Trường của bạn được khởi tạo trong sự kiện Page_Load

+0

Tôi hiểu rõ. Cảm ơn ví dụ của bạn. – megazero

+0

Bạn được chào đón @jerry – Habib

4

Trong trường hợp đầu tiên bạn khởi tạo biến tại vị trí khai báo.

Trong giây, bạn khởi tạo nó trong một hàm tạo.

Sự khác biệt chính là nếu bạn có các hàm tạo bổ sung và quên khởi tạo hoặc nối chuỗi các hàm tạo, bạn có thể có một biến chưa được khởi tạo.

+0

tốt, một biến khởi tạo mặc định (T) mà là null với nhiều loại tài liệu tham khảo. .in C# bạn không thể giữ một biến uninitialized (dễ dàng). – eFloh

2

Sự khác biệt duy nhất là thứ tự các đối tượng được tạo. Nếu tôi nhớ rõ, các trình khởi tạo trường được chạy trước hàm tạo, để nếu hàm tạo tham chiếu trường, nó đã có sẵn.

Nhưng từ 99,9% trường hợp, bạn sẽ không thấy sự khác biệt giữa hai trường hợp. Trong hầu hết trường hợp, an toàn hơn để khởi tạo trường của bạn trực tiếp trên nó, nó sẽ ngăn bạn quên nó trong trường hợp của nhiều hàm tạo hoặc lớp dẫn xuất và phân cấp phức tạp.

Thông thường, các hàm tạo được sử dụng để lấy các tham số bên ngoài để điền vào các trường không thể có trình khởi tạo trường.

+0

Trải nghiệm tốt cho tôi. Khởi tạo trường trực tiếp trên đó, cảm ơn bạn rất nhiều. – megazero

0

Bạn sẽ có unintialized variable for second case nếu bạn sử dụng hàm tạo khác với hàm tạo mặc định cho đối tượng khởi tạo -

Data data = new Data(5); 

Nhưng nếu bạn chain parametized constructors to call default constructor như thế này -

class Data 
{ 
    PersonDataContext persons; 
    public Data() 
    { 
     persons = new PersonDataContext(); 
    } 

    public Data(int a) : this() 
    { 

    } 
} 

biến persons sẽ được khởi tạo.

0

Trong ví dụ đầu tiên của bạn sẽ không có sự khác biệt hiệu quả miễn là Constructor là Constructor duy nhất. Nếu bạn thêm các Constructors khác thì bạn cần phải chắc chắn rằng tất cả chúng khởi tạo trường 'người'.

Trong ví dụ ASP.NET (cho đoạn mã thứ hai) - bạn đang khởi tạo trường 'người' trong phương thức Page_Load, có nghĩa là bất kỳ phương pháp nào khác sử dụng trường này có thể tìm thấy nó chưa được khởi tạo. (Ý của bạn là Page_Load, hoặc bạn có ý định biến nó thành một Constructor ...?)

Dòng dưới cùng là, nếu trường 'người' luôn cần phải không rỗng, thì an toàn hơn để khởi tạo như một Trình khởi tạo trường ...

3

Trong ví dụ thứ hai của bạn, sự khác biệt chính là Page_Load chỉ là một trong nhiều sự kiện ASP.NET được gọi khi xử lý yêu cầu. Do đó, các sự kiện được nâng lên trước khi Page_Load sẽ không thể truy cập/sử dụng trường này, vì nó chưa được khởi tạo.

Kiểm tra ASP.NET Trang chu: http://msdn.microsoft.com/en-us/library/ms178472%28v=vs.100%29.aspx

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