2000'li yıllarda bir meslektaşım bana kamu yöntemlerini sanal veya soyut yapmanın bir anti-desen olduğunu söyledi.
Örneğin, iyi tasarlanmamış böyle bir sınıfı düşündü:
public abstract class PublicAbstractOrVirtual
{
public abstract void Method1(string argument);
public virtual void Method2(string argument)
{
if (argument == null) throw new ArgumentNullException(nameof(argument));
// default implementation
}
}
Dedi ki;
- uygulanan
Method1
ve geçersiz kılan türetilmiş bir sınıfın geliştiricisiMethod2
, argüman doğrulamasını tekrarlamak zorundadır. - temel sınıf geliştiricisinin
Method1
veyaMethod2
daha sonra özelleştirilebilir kısmına bir şey eklemeye karar vermesi durumunda bunu yapamaz.
Bunun yerine meslektaşım bu yaklaşımı önerdi:
public abstract class ProtectedAbstractOrVirtual
{
public void Method1(string argument)
{
if (argument == null) throw new ArgumentNullException(nameof(argument));
this.Method1Core(argument);
}
public void Method2(string argument)
{
if (argument == null) throw new ArgumentNullException(nameof(argument));
this.Method2Core(argument);
}
protected abstract void Method1Core(string argument);
protected virtual void Method2Core(string argument)
{
// default implementation
}
}
Bana kamusal yöntemleri (veya mülkleri) sanal veya soyut yapmanın alanları kamusal yapmak kadar kötü olduğunu söyledi. Alanları mülklere sararak, gerekirse daha sonra bu alanlara herhangi bir erişimi engelleyebilir. Aynı durum genel sanal / soyut üyeler için de geçerlidir: onları ProtectedAbstractOrVirtual
sınıfta gösterildiği gibi sarmalamak temel sınıf geliştiricisinin sanal / soyut yöntemlere giden çağrıları durdurmasına izin verir.
Ama bunu bir tasarım kılavuzu olarak görmüyorum. Microsoft bile bunu izlemez: Bunu Stream
doğrulamak için sınıfa bir göz atın .
Bu rehber hakkında ne düşünüyorsun? Herhangi bir anlam ifade ediyor mu veya API'yı aşırı karmaşıklaştırdığını mı düşünüyorsunuz?
protected
soyut sınıfın özel üyelerini türetilmiş sınıflara maruz bırakmak istediğinizde en kullanışlıdır. Her durumda, özellikle arkadaşınızın görüşü hakkında endişelenmiyorum; özel durumunuz için en anlamlı erişim değiştiriciyi seçin.
virtual
isteğe bağlı geçersiz kılmaya izin verir. Yönteminiz büyük olasılıkla herkese açık olmalıdır, çünkü geçersiz kılmayabilir. Yöntemler yapmakabstract
onları geçersiz kılmaya zorlar; muhtemelen olmalıprotected
, çünkü birpublic
bağlamda özellikle yararlı değiller .