Câu trả lời của tôi: sự lựa chọn thiết kế kém. ;-)
Đây là một cuộc tranh luận thú vị tập trung vào tác động cú pháp. Cốt lõi của đối số, theo quan điểm của tôi, là một quyết định thiết kế dẫn đến các lớp tĩnh được niêm phong. Tập trung vào tính minh bạch của tên lớp tĩnh xuất hiện ở cấp cao nhất thay vì ẩn ('khó hiểu') đằng sau tên con? Người ta có thể hình ảnh một triển khai ngôn ngữ có thể truy cập trực tiếp vào cơ sở hoặc trẻ em, gây nhầm lẫn.
Một ví dụ giả, giả sử kế thừa tĩnh được định nghĩa theo một cách nào đó.
public static class MyStaticBase
{
SomeType AttributeBase;
}
public static class MyStaticChild : MyStaticBase
{
SomeType AttributeChild;
}
Sẽ dẫn đến:
// ...
DoSomethingTo(MyStaticBase.AttributeBase);
// ...
cái nào có thể (sẽ?) tác động đến việc lưu trữ giống như
// ...
DoSomethingTo(MyStaticChild.AttributeBase);
// ...
Rất bối rối!
Nhưng chờ đã! Trình biên dịch sẽ xử lý MyStaticBase và MyStaticChild như thế nào có cùng chữ ký được xác định trong cả hai? Nếu đứa trẻ ghi đè hơn ví dụ trên của tôi sẽ KHÔNG thay đổi cùng một bộ lưu trữ, có thể? Điều này dẫn đến sự nhầm lẫn nhiều hơn.
Tôi tin rằng có một sự biện minh không gian thông tin mạnh mẽ cho sự kế thừa tĩnh hạn chế. Thêm về các giới hạn trong thời gian ngắn. Mã giả này hiển thị giá trị:
public static class MyStaticBase<T>
{
public static T Payload;
public static void Load(StorageSpecs);
public static void Save(StorageSpecs);
public static SomeType AttributeBase
public static SomeType MethodBase(){/*...*/};
}
Sau đó, bạn nhận được:
public static class MyStaticChild : MyStaticBase<MyChildPlayloadType>
{
public static SomeType AttributeChild;
public static SomeType SomeChildMethod(){/*...*/};
// No need to create the PlayLoad, Load(), and Save().
// You, 'should' be prevented from creating them, more on this in a sec...
}
Cách sử dụng trông như:
// ...
MyStaticChild.Load(FileNamePath);
MyStaticChild.Save(FileNamePath);
doSomeThing(MyStaticChild.Payload.Attribute);
doSomething(MyStaticChild.AttributeBase);
doSomeThing(MyStaticChild.AttributeChild);
// ...
Người tạo ra đứa trẻ tĩnh không cần phải suy nghĩ về quá trình tuần tự hóa miễn là họ hiểu bất kỳ giới hạn nào có thể được đặt trên công cụ tuần tự hóa của nền tảng hoặc môi trường.
Statics (singletons và các dạng khác của 'toàn cầu') thường xuất hiện xung quanh bộ lưu trữ cấu hình. Kế thừa tĩnh sẽ cho phép loại phân bổ trách nhiệm này được thể hiện rõ ràng trong cú pháp để phù hợp với cấu trúc phân cấp. Mặc dù, như tôi đã chỉ ra, có rất nhiều tiềm năng cho sự mơ hồ lớn nếu các khái niệm kế thừa tĩnh cơ bản được thực hiện.
Tôi tin rằng sự lựa chọn thiết kế phù hợp sẽ là cho phép kế thừa tĩnh với những hạn chế cụ thể:
- Không ghi đè bất cứ điều gì. Đứa trẻ không thể thay thế các thuộc tính cơ sở, trường hoặc phương thức, ... Quá tải sẽ ổn, miễn là có sự khác biệt về chữ ký cho phép trình biên dịch sắp xếp con so với cơ sở.
- Chỉ cho phép các cơ sở tĩnh chung, bạn không thể kế thừa từ một cơ sở tĩnh không chung chung.
Bạn vẫn có thể thay đổi cùng một cửa hàng thông qua một tài liệu tham khảo chung MyStaticBase<ChildPayload>.SomeBaseField
. Nhưng bạn sẽ không được khuyến khích vì loại chung sẽ phải được chỉ định. Trong khi tham chiếu con sẽ sạch hơn : MyStaticChild.SomeBaseField
.
Tôi không phải là người viết trình biên dịch nên tôi không chắc mình có thiếu điều gì về những khó khăn khi thực hiện những hạn chế này trong trình biên dịch hay không. Điều đó nói rằng, tôi là một người tin tưởng mạnh mẽ rằng có một không gian thông tin cần có sự kế thừa tĩnh hạn chế và câu trả lời cơ bản là bạn không thể vì một lựa chọn thiết kế kém (hoặc quá đơn giản).