简体   繁体   English

我可以对一个抽象类进行子类化,而该抽象类又具有另一个子类吗? (C#)

[英]Can I subclass a abstract class which has another abstract class which is also subclassed? (C#)

Lets say I want to design a abstract system for counting sections in a document. 可以说我想设计一个抽象系统来对文档中的部分进行计数。 I designed two classes, Document and Section , the document has a list of sections and a method to count them. 我设计了两个类, DocumentSection ,该文档有一个节列表和一个计算它们的方法。

public abstract class Document {
  List<Section> sections;

  public void addSection(Section section) { 
    sections.Add(section);
  }
  public int sectionCount() { 
    return sections.count;
  } 
}
public abstract class Section {
  public string Text;
}

Now, I want to be able to use this code in multipe scenarios. 现在,我希望能够在多重场景中使用此代码。 For example, I have Books with Chapters. 例如,我有带有章节的书。 The Book would be a subclass of Document, and Chapter a subclass of Section. 该书将是Document的子类,而Chapter将是Section的子类。 Both classes will contain extra fields and functionality, unrelated to the counting of sections. 这两个类都将包含与字段计数无关的额外字段和功能。

The problem I stumble upon now is that because Document contains sections, and not Chapters, the added functionality of Chapter is useless to me, it can only added as a section to Book. 我现在偶然发现的问题是,因为文档包含章节而不是章节,所以章节的添加功能对我来说毫无用处,因此只能将其作为章节添加到Book中。

I was reading about downcasting, but really think this is not the right way to go. 我当时在阅读有关垂头丧气的文章,但实际上认为这不是正确的方法。 I'm thinking maybe I took the wrong approach altogether. 我在想也许我完全采用了错误的方法。

My question comes to this: How do I design such an abstract system, that can be reused by subclassed objects, and is this the way to go? 我的问题是这样的:我如何设计这样一个抽象系统,该系统可以被子类对象重用,这是可行的方法吗?

You need generics: 您需要泛型:

public abstract class Document<T> where T : Section

public abstract class Section

public class Book : Document<Chapter>

public class Chapter : Section

You might also want to make a section know what kind of document it can be part of. 您可能想让一个部分知道它可以属于哪种类型的文档。 Unfortunately that becomes a lot more complicated: 不幸的是,这变得更加复杂:

public abstract class Document<TDocument, TSection>
    where TDocument : Document<TDocument, TSection>
    where TSection : Section<TDocument, TSection>

public abstract class Section<TDocument, TSection>
    where TDocument : Document<TDocument, TSection>
    where TSection : Section<TDocument, TSection>

public class Book : Document<Book, Chapter>

public class Chapter : Section<Book, Chapter>

I've had to do this in Protocol Buffers, and it's messy - but it does allow you to reference both ways in a strongly-typed way. 我必须在协议缓冲区中执行此操作,而且比较麻烦-但是它确实允许您以强类型的方式引用这两种方式。 I'd go for the first version if you can get away with it. 如果可以的话,我会选择第一个版本的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM