2
下面模型(右側)中的PartyRoleConstraints類是此問題的主題。泛型能改進這種設計嗎?
的想法是,當一個客戶端嘗試參加一個聚會,一個角色類型相關聯,該角色類型查看其是否有應防止某一締約方被相關的任何約束。締約方是個人和組織的超類型。
這裏是完全通用的接口,我以後:
public interface IRoleConstraint<in T>
{
Func<T, bool> IsSatisfied { get; }
string UnsatisfiedDescription { get; }
bool CanAddRole(T instance);
}
一個共同的約束將是類型。所以如果我有角色類型的「丈夫」,那麼我想確保黨的實例是一個人。下面是一些實施和測試案例,證明我可以做到這一點:
public class RoleConstraint<T> : IRoleConstraint<T>
{
public RoleConstraint(Func<T, Boolean> isSatisfied, string unsatisfiedDescription) {
if (isSatisfied == null) throw new ArgumentNullException("isSatisfied");
if (unsatisfiedDescription == null) throw new ArgumentNullException("unsatisfiedDescription");
IsSatisfied = isSatisfied;
UnsatisfiedDescription = unsatisfiedDescription;
}
public Func<T, bool> IsSatisfied { get; protected set; }
public string UnsatisfiedDescription { get; protected set; }
public bool CanAddRole(T instance) { return IsSatisfied.Invoke(instance); }
}
public class PartyRoleConstraint : RoleConstraint<Party>
{
public PartyRoleConstraint(Func<Party, bool> isSatisfied, string unsatisfiedDescription) : base(isSatisfied, unsatisfiedDescription) { }
}
public class PartyRoleConstrainedToType<TRequired> : PartyRoleConstraint where TRequired : Party
{
private static readonly string _unsatisfiedDescription
= string.Format("This role requires a Party instance to be a {0}", typeof(TRequired).Name);
private static readonly Func<Party, bool> _isSatisfied = instance => instance.GetType().Equals(typeof(TRequired));
public PartyRoleConstrainedToType() : base(_isSatisfied, _unsatisfiedDescription) { }
}
[Test]
public void Constraints_IfTypeConstraint_and_InstanceDoesNotMatch_False()
{
var sony = new Organization("Sony Corporation");
var constraint = new PartyRoleConstrainedToType<Person>();
_husbandRoleType.AddConstraint(constraint);
Assert.That(_husbandRoleType.CanAddRole(sony), Is.False);
}
我打的問題是,如果我想建立一個基於黨的子類型的屬性的規則。例如,我想讓丈夫的性別爲男性。我可以用投這樣做,因爲:
[Test]
public void Constraints_IfConstraintConditionIsNotMet_False()
{
_husbandRoleType.AddConstraint(new PartyRoleConstrainedToType<Person>());
Assert.That(_husbandRoleType.CanAddRole(_arthur), Is.True);
//**** here is the cast **** //
var mustBeMale = new PartyRoleConstraint(p => ((Person)p).Gender == Gender.Male, "the husband must be male.");
_husbandRoleType.AddConstraint(mustBeMale);
Assert.That(_husbandRoleType.CanAddRole(_arthur), Is.False);
_arthur.Gender = Gender.Male;
Assert.That(_husbandRoleType.CanAddRole(_arthur), Is.True);
}
的問題(!終於)是:我可以使用泛型以避免投,如果是這樣,怎麼樣?
我真的想知道是否可以使它成爲類類型參數的一部分,因爲這是跨越幾個應用程序的框架類型庫的一部分。沒有想到一般的流利類型的東西,這正是我想你所說的。那對於是一個嵌套類?你可以添加幾行代碼來幫助我更好地看到它嗎? –
Berryl
子類化給定的約束,比如ie,新的MustMatchGender(Gender.Male)對於給定域中的更常見的約束可能是最好的,但是想要更好地理解你提出的更好的約束。乾杯 – Berryl