2010-04-02 3 views
1

Мне нужно сделать экспорт из базы данных в CSV. (.NET 2)Обработка динамического поля

field; fileld; field... etc 

Есть 3 типа полей: Альфа, Числовой и BOOL respresented в "alphaValue", intValue и True/False.

Я стараюсь, чтобы инкапсулировать это в семействе полого для того, чтобы экспортировать, если альфа затем установите «», если Bool => True/False, если числовой пусть как есть.

и попытаться построить CsvField класс:

Public Structure?Class CsvField(Of T As ???) 

    End Structure 

    Enum FieldType 
    Alpha 
    Bool 
    Numeric 
    End Enum 

possibile использование:

myCollection.Add(new CsvField(DateTime.Now, FileType.Alpha)) 
myCollection.Add(new CsvField(myInt, FileType.Numeric)) 

любые предложения приветствуются.

ответ

2

Не требуется никаких дженериков. Просто используйте наследование:

' abstract base class; you could possibly declare it as an interface instead: ' 
MustInherit Class CsvField 
    Public MustOverride Function Export() As String 
End Class 


' specialized class for alpha-numeric fields: ' 
Class AlphaCsvField : Inherits CsvField 
    ... 
    Public Overrides Function Export() As String 
     Return String.Format("""{0}""", value) 
    End Function 

    Private value As String 
End Class 


' specialized class for bool fields ' 
Class BoolCsvField : Inherits CsvField 
    ... 
    Public Overrides Function Export() As String 
     If value = True Then 
      Return "True" 
     Else 
      Return "False" 
     End If 
    End Function 

    Private value As Boolean 
End Class 

... 

Пример кода предполагает, что value сохраняет фактическое значение поля. Надеюсь, что этот пример достаточно ясен. Сделайте свою коллекцию полей одной для типа базового класса типа, например. List(Of CsvField). Затем он может содержать объекты всех производных типов.


Btw., Обратите внимание, как при использовании polymorphism, вы можете быть в состоянии избавиться от FieldType перечисления полностью и все If/Select Case конструкции, которые принимают решение о том, что делать в зависимости от типа поля. Если вам все еще нужно, чтобы сделать это, вы могли бы заменить:

If someCsvField.FieldType = Alpha Then ... 

с

If TypeOf someCsvField Is AlphaCsvField Then ... 

Однако, как правило, должны быть в состоянии переместить такую ​​логику в производных классах и избавиться от If заявлений переопределяющие методы. В этом весь смысл приведенного выше примера.


P.S .: В случае, если вам интересно, как вы создаете ваши CsvField объекты без проверки явно от типа. Один из способов заключается в использовании фабричных методов и перегрузки методов:

MustInherit Class CsvField 

    Public Shared Function Create(value As String) As CsvField 
     Return New AlphaCsvField(value) 
    End 

    Public Shared Function Create(value As Boolean) As CsvField 
     Return New BoolCsvField(value) 
    End 

    ... 

    ' as in the above code example ' 
    Public MustOverride Function Export() As String 

End Class 

Например, CsvField.Create(False) создало бы BoolCsvField «замаскирован», как CsvField, так что вы можете поместить его внутри List(Of CsvField) или любой коллекции у вас есть.

+0

является полиморфизмом больше ресурсов и занимает много времени, что простой класс с типом? – serhio

+0

@serhio no, при использовании наследования и полиморфизма нет никакого ресурса или штрафа за производительность. –

+0

@serhio: Нет, или, по крайней мере, дополнительные * накладные расходы * памяти были бы настолько малы, чтобы быть незначительными в вашем случае (скорее всего).Runtime * performance * может даже немного улучшиться. Не беспокойтесь об этом. Использование наследования приведет к получению более структурированного, более легкого для чтения и, следовательно, более поддерживаемого кода, что более важно, чем несколько дополнительных использованных байтов в памяти. Если вас все еще интересует причина этого, я могу предоставить более подробную информацию по запросу. – stakx

Смежные вопросы