Дублирование кода относится к значительному повторению блоков, операторов или даже групп общих объявлений членов. Это не относится к повторению ключевых слов, идентификаторов, шаблонов и т. Д. В противном случае вы не сможете достичь полиморфизма.
Пример, который вы предоставляете, на самом деле не демонстрирует принцип Open / Closed, потому что вы не продемонстрировали, как поведение данного класса может быть расширено без модификации. Принцип Open / Closed заключается в создании новых классов каждый раз, когда требуется вариант поведения. Это может быть достигнуто с помощью наследования вместе с шаблоном Template Method (т. Е. Путем вызова абстрактных или виртуальных методов в базовом классе, которые переопределяются в подклассах для достижения желаемого / нового поведения), но чаще это демонстрируется с использованием композиции с использованием шаблона Strategy (т.е. инкапсуляция варианта поведения в классе и передача его закрытому типу для использования при определении общего достигнутого поведения).
Из вашего примера видно, что вы больше размышляли о попытках достижения OCP с помощью наследования, но, начиная с базового средства форматирования отчетов, чтобы установить интерфейс с подтипами для указания различных типов форматов для данного отчета, на самом деле хорошее начало, чтобы показать OCP через композицию. Для демонстрации OCP с композиционным подходом необходим класс, который использует средства форматирования ... скажем, ReportWriter.
public class ReportWriter : IReportWriter
{
Write(IReportData data, IReportFormatter reportFormatter)
{
// ...
var formattedStream = reportFormatter.Format(data, stream);
// ...
}
}
Просто для демонстрации я сделал несколько предположений о том, как может вести себя наш новый форматер, поэтому не зацикливайтесь на этой части. Особое внимание следует уделить тому, что ReportWriter открыт для расширения, позволяя передавать новые средства форматирования, что влияет на то, как отчеты в конечном итоге пишутся, но закрывается для изменения кода, необходимого для достижения этого нового поведения (то есть наличия операторов if, switch заявления и т. д. для достижения нескольких способов форматирования).
Мало того, что принцип Open / Closed не только не вызывает дублирование кода, но достигается за счет использования композиции вместо наследования, но на самом деле может помочь уменьшить дублирование. Если в ходе создания иерархии наследования или классов стратегии происходит истинное дублирование кода, это указывает на проблему факторинга, не связанную с тем фактом, что она может существовать в контексте вашей попытки достижения OCP.