2016-08-16 9 views
0

У меня есть два класса:Располагая базовый класс, прежде чем унаследовал класс

public abstract class UnitOfWorkBase: IDisposable { } 
public sealed class UnitOfWorkSql: UnitOfWorkBase { } 

метод производного класса Dispose обычно выглядит следующим образом:

protected override void Dispose (bool disposing) 
{ 
    if (!this.Disposed) 
    { 
     if (disposing) 
     { 
      // Managed. 
     } 

     // Unmanaged. 

     this.Disposed = true; 
    } 

    base.Dispose(disposing); 
} 

Я всегда видел вызов base.Dispose(disposing) в конец метода. Однако, в недавнем случае, существует необходимость располагать объекты базового класса перед тем объектов производного класса следующим образом:

protected override void Dispose (bool disposing) 
{ 
    base.Dispose(disposing); 

    if (!this.Disposed) 
    { 
     if (disposing) 
     { 
      // Managed. 
     } 

     // Unmanaged. 

     this.Disposed = true; 
    } 
} 

Я не уверен, если это считается плохой практикой. Есть ли что-то, на что можно обратить внимание?

+3

Я подозреваю, что вы не видите этот вариант, потому что это необычно для этого требования. Не могли бы вы рассказать немного больше о том, почему базовый класс * нуждается в '' Dispose'? Это будет означать, что у вас есть несколько наборов классов с необычным временем жизни или отношениями. –

+0

@Damien_The_Unbeliever: Я объясню контекст в последующем сообщении. Между тем, вы видите какие-то общие gotchas с этим вариантом? –

+0

@Damien_The_Unbeliever: класс 'UnitOfWorkBase' содержит общий объект IDbTransaction, в то время как класс' UnitOfWorkSql' содержит конкретный объект 'DbContext'. Я решил сохранить объект транзакции в базовом классе, так как все предсказуемые платформы баз данных будут использовать 'IDbTransaction'. Кроме того, я не хочу раскрывать фактический объект транзакции как «public» или «protected». Таким образом, класс 'UnitOfWorkSql' всегда заключен в оператор' using', тогда как объект транзакции 'private' должен быть удален первым. Надеюсь, это имеет смысл. –

ответ

1

Думаю, вы должны сломать обычный образец здесь. Вместо того, чтобы:

class BaseClass 
{ 
    protected virtual void Dispose(bool disposing) 
    { 
     if (disposing) 
     { 
      //dispose my resources 
     } 
    } 
} 

написать что-то вроде:

class BaseClass 
{ 
    private void Dispose(bool disposing) 
    { 
     if (disposing) 
     { 
      //dispose my resources 
      DisposeManagedOverride(); 
     } 

     CloseUnmanagedOverride(); 
    } 

    protected virtual void DisposeManagedOverride() {} 

    protected virtual void CloseUnmanagedOverride() {} 
} 

Таким образом, вы обеспечите надлежащий порядок освобождения ресурсов.