我甚至不确定要搜索什么关于这个问题,所以我想我会在这里发布。这是动态类还是...?
比方说,我有一大堆的接口等...
/// <summary>
/// All interesting classes will implement this interface
/// </summary>
interface IMasterInterface {}
/// <summary>
/// Interface to represent someone that creates/produces goods
/// </summary>
interface IProduceGoods : IMasterInterface { int Prop1 {get;} }
/// <summary>
/// Interface to represent someone that buys/consumes goods
/// </summary>
interface IConsumeGoods : IMasterInterface { int Prop2 {get;} }
/// <summary>
/// Interface to represent someone that stores goods
/// </summary>
interface IStoreGoods : IMasterInterface { double Prop3 {get;} string name {get;}}
/// <summary>
/// Interface to represent someone that enjoys looking at goods
/// </summary>
interface IEnjoyLookingAtGoods : IMasterInterface { int Prop4 {get;} DateTime Prop5 {get;} }
现在,我今天一定的组合,我知道我想要的,是这样的:
/// <summary>
/// Class to represent a farm which grows and stores crops
/// </summary>
class Farm : IProduceGoods, IStoreGoods {/*...*/}
/// <summary>
/// Class to represent a merchant who buys goods and stores them
/// </summary>
class Merchant : IConsumeGoods, IStoreGoods {/*...*/}
/// <summary>
/// Window Shopper represents someone who doesn't buy anything and only looks
/// </summary>
class WindowShopper : IEnjoyLookingAtGoods{ /*...*/ }
现在我很高兴我有几堂课,但明天我想,如果有人从商家那里买了一堂课,那么我会去我的代码,然后加上
/// <summary>
/// Princesses have lots of money to buy stuff and lots of time to look at stuff
/// </summary>
class Princess : IEnjoyLookingAtGoods, IConsumeGoods {/*...*/}
现在,我不认为我应该这样做...
我希望做的是有一个工厂(或类似)的事情,并说:
IMasterInterface princess = MyFactory.Create(IEnjoyLookingAtGoods, IEnjoyLookingAtGoodsParameters, IConsumeGoods, IConsumeGoodsParameters)
/// This should be true
((princess is IEnjoyLookingAtGoods) && (princess is IConsumeGoods))
从本质上讲,我想告诉工厂使用哪些接口来构建对象。我有容器有IMasterInterface列表
/// <summary>
/// My container class for interesting objects
/// </summary>
class InterestingObjectContainer
{ public ReadOnlyCollection<IMasterInterface> InterestingObjects {get;} }
现在,这里是问题的关键所在。让所有感兴趣的类实现IMasterInterface的原因是能够拥有一个List并使用更具体的接口作为过滤器。或许下面会更清楚:
/// <summary>
/// I want to see the net population of producers and get there total production
/// </summary>
class ProducerProductionCalculator
{
// THIS IS WHERE THE MEAT OF THE QUESTION RESIDES!
ProductionResults Calculate(InterestingObjectContainer interestingObject)
{
List<IProduceGoods> producers = interestingObject.InterestingObjects.OfType<IProduceGoods>(); // Perhaps more interest LINQ
return DoSomethingWithListToAggregate(producers);
}
}
通过滤除,以更具体的接口,我可以传递给 DoSomethingWithListToAggregate(ICollection的生产商)的所有对象的IProduceGoods的 具有方法/属性现在算类。
我想过用字典和字符串属性查找来实现这一点,但感觉就像我可以用这种方式编写更强大的类型化代码,并确保在某处存在一个简单的拼写错误不会混淆所有内容。
总之,我想总结的是:
这是实施对象上不同属性的一个好办法,如果因此这将是一个更好的。如果没有,是否有办法在工厂中创建对象,正如我上面试图解释的那样?
编辑:
我看到一些OKS到这样的想法,这很酷。我想知道如何创建一个只有属性的接口的参数,并且属性只有getter(我认为这很重要)以及属性的属性值,并返回一个实现该接口的对象并具有所有属性定义的属性。
例如,
/// <summary>
/// Factory to create any combination of properties
/// </summary>
class FactoryForInterestingObjects
{
public static IMasterInterface Create(
List<KeyValuePair</*what goes here is the interface that I want to use,
what goes here are the parameter values that
should be returned by the getter */>>);
}
我合格出厂的所有接口和它们的参数值,它会创建一些类实现这些接口并具有这些值。希望这个更清楚一点?
编辑2:如何使用装饰者?
从我看到的装饰器中,您可以扩展对象的功能。这很酷。但是,您必须提前知道如何扩展该功能。你不能任意做这件事。
请考虑我的代码库如上,我想使用装饰器。
我会说:
// Edited to be correct
class EnjoyLookingDecorator : IEnjoyLookingAtGoods
{
private IMasterInterface instance;
public EnjoyLookingDecorator(IMasterInterface wrappedObject)
{ this.instance = wrapped Object;}
#region Implementation of IEnjoyLookingAtGoods
/*...*/
#endregion
}
编辑4:
我仍然不认为这会工作。在你的例子中,我失去了包含的类接口,我不得不重定向它。例如,
class EnjoyLookingDecorator : IEnjoyLookingAtGoods
{
private IMasterInterface instance;
public EnjoyLookingDecorator(IMasterInterface concrete)
{ this.instance = concrete;}
#region Implementation of IEnjoyLookingAtGoods here
/*...*/
#endregion
bool Is<T>() //this should be in the IMasterInterface
{
return this is T or instance is T;
}
}
class ConsumesGoodsDecorator : IConsumeGoods
{
private IMasterInterface instance;
public ConsumesGoodsDecorator (IMasterInterface concrete)
{ this.instance = concrete;}
#region Implementation of IConsumeGoods here
/*...*/
#endregion
bool Is<T>()
{
return this is T or instance is T;
}
}
所以当你D
IMasterInterface princess = new MasterClass() //whatever your concrete type is named
princess = new ConsumesGoodsDecorator(new EnjoyLookingDecorator(princess))
你不再能做到princess.PropertyOnIEnjoyLookingDecoratorInterface你失去所有这些属性。这不是我想要的。保留属性的唯一方法是重定向
class ConsumesGoodsDecorator : IConsumeGoods, IEnjoyLookingAtGoods
{
private IMasterInterface instance;
public ConsumesGoodsDecorator (IMasterInterface concrete)
{ this.instance = concrete;}
#region Implementation of IConsumeGoods here
/*...*/
#endregion
#region Redirect all the IEnjoyLookingAtGoods Property Getters to instance
/* ... */
#endregion
bool Is<T>()
{
return this is T or instance is T;
}
}
通过执行重定向,我们必须实现接口。然后组合必须都有代码,这正是我想要避免的。我不会对接口的组合有任何限制。
编辑5:
也许我仍然不清楚我的问题。试想接口,因为它们上面有它们的属性填充
如果工厂可以做这样的事情:
/// <summary>
/// Factory to create any combination of properties
/// </summary>
class FactoryForInterestingObjects
{
public static IMasterInterface Create(
List<KeyValuePair<Type t, ArgSet customArguments>> interfaces))
{
object baseObject;
foreach(KeyValuePair<Type, ArgSet> interface in interfaces)
{
AddInterface(interface, object);
}
}
private static void AddInterface(KeyValuePair<Type, ArgSet> interface, ArgSet arguments)
{
// Delegate this to someone else
if(interface.Key is typeof(IProduceGoods))
{
IProduceGoodsExtensions.AddInterface(o, interface.value);
}
}
}
public static class IProduceGoodsExtensions
{
public static void AddInterface(object o, ArgSet arguments)
{
// do something to object to make it implement IProductGoods
// and make all the getters return the arguments passed in ArgSet
}
}
我知道这是不是它是如何将实际工作,但足以说明我点试图制造。我希望对象实现接口的动态组合,并为设置者设置默认值。
即使我能这样做有工厂编写包含代码的文本文件:
/// <summary>
/// Auto Generated by Factory to create a new type on the fly
/// </summary>
class ClassImplementingIProduceGoodsAndIEnjoyLookingAtGoods : IProduceGoods, IEnjoyLookingAtGoods
{
// From IProduceGoods
public int Prop1 {get; private set;}
// From IEnjoyLookingAtGoods
public int Prop4 {get; private set;}
public DateTime Prop5 {get; private set;}
public ClassImplementingIProduceGoodsAndIEnjoyLookingAtGoods(int prop1, int Prop4 , DateTime Prop5)
{
this.Prop1 = prop1; this.Prop4 = Prop4; this.Prop5 = Prop5;
}
}
然后编译类,并以某种方式让我来创建它的实例。这就是我要找的。希望这更有意义。
编辑6:
这是解决方案,我可能会以来,我没有看到在这一点上的替代去。现在
//Update Master Interface
interface IMasterInterface
{
bool Is(Type t);
IMasterInterface As(Type t);
}
/// <summary>
/// Class to build up a final object
/// </summary>
class CompositionObject : IMasterInterface
{
ICollection<IMasterInterface> parts;
CompositionObject(IMasterInterface object){ parts = new List<IMasterInterface(object);}
bool Is(Type t)
{
foreach(IMasterInterface part in parts)
{ if (part is t) return true; // not sure on this off top of head
}
return false;
}
IMasterInterface As(Type t)
{
foreach(IMasterInterface part in parts)
{ if(part is t) return part; }
}
bool Add(IMasterInterface interface)
{ this.Is(typeof(interface)) return false; // don't add again
this.parts.Add(interface) }
}
我厂可以只返回这些组成对象只要作为被调用,我可以再低垂安全。我觉得可能有一种方法可以使用泛型来避免投射。
实现IMasterInterface的任何具体类都可以在调用As时简单地返回自己。编辑3:
感谢大家的意见。我很高兴我发布了我对模式的无知; D感谢您的澄清!我喜欢这个网站和你所有可爱的人!
为什么你不能与做法最终你使用'InterestingObjects.OfType()'提及? –
sll
@sll:我不知道如何制造工厂。这就是问题所在。或者如果这是一个好方法。 – MPavlak
你期望在所有这些接口之间有什么不同?除了getters? –