This is probably easiest to explain with code (this is of course not the actual code but it has the same properties):
I have an interface that looks something like this:
public interface ISomeProvider
{
object GetFoo1(); //<-- This needs caching
//These others don't
object GetFoo2();
object GetFoo3();
//And let's say 20 more
}
And this has an implementation like this:
//NOTE: Sealed class otherwise we could inherit from it
public sealed class SuperCleverProvider : ISomeProvider
{
public object GetFoo1()
{
return "a";
}
public object GetFoo2()
{
return "b";
}
public object GetFoo3()
{
return "b";
}
}
Now one of these calls, let's say GetFoo1 is really heavy so I want to provider a new version of the interface where calls to it are cached using an instance of the old one.
I'm doing it like this at the moment:
public class CachedSuperCleverProvider : ISomeProvider
{
private readonly SuperCleverProvider _provider;
public CachedSuperCleverProvider(SuperCleverProvider provider)
{
_provider = provider;
}
private object UsingCache<T>(string cacheKey, Func<T> eval)
{
//Pretend this does caching. This is not related to the question
throw new NotImplementedException();
}
public object GetFoo1()
{
return UsingCache("foo1", _provider.GetFoo1);
}
//The code below this point is what I want to get rid of
public object GetFoo2()
{
return _provider.GetFoo2();
}
public object GetFoo3()
{
return _provider.GetFoo3();
}
//And so on for all the rest
}
This has two problems (at least):
Every time someone adds a method to the interface I have to go change this even though I dont want this new method to be cached
I get this huge list of useless code that just call through to the underlying implementation.
Can anyone think of a way of doing this that doesn't have these problems?
Three options:
Autogenerate the class
Use PostSharp or something similar to do it in a more interceptor-based way
Live with it
Personally I'd probably go with the third option, unless you really find yourself doing this a lot. Weigh up the cost of each option - how much time are you actually going to spend adding this delegation?
Personally I'd like to see this sort of thing as a language feature - "delegate to this interface via this field unless I override it" but obviously that's not present at the moment...
Here's what I'd suggest. It's not too much better, but will simplify the wrapping process.
Create a class SomeProviderWrapper:
public class SomeProviderWrapper : ISomeProvider
{
protected ISomeProvider WrappedProvider { get; private set; }
protected SomeProviderWrapper(ISomeProvider wrapped)
{
if (wrapped == null)
throw new ArgumentNullException("wrapped");
WrappedProvider = wrapped;
}
public virtual object GetFoo1()
{
return WrappedProvider.GetFoo1();
}
public virtual object GetFoo2()
{
return WrappedProvider.GetFoo2();
}
public virtual object GetFoo3()
{
return WrappedProvider.GetFoo3();
}
}
Now that the wrapping is relegated to its own class, you can write the caching version:
public class CachedSuperCleverProvider : SomeProviderWrapper
{
public CachedSuperCleverProvider(ISomeProvider wrapped) : base(wrapped) { }
private object UsingCache<T>(string cacheKey, Func<T> eval)
{
throw new NotImplementedException();
}
public override object GetFoo1()
{
return UsingCache("foo1", WrappedProvider.GetFoo1);
}
}
This keeps the delegation code out of your super clever provider. You will still have to maintain the delegation code, but it won't pollute the design of your caching provider.
Related
I'm having a hard time understanding the implementation of client code with the factory method. I understand the overall use of Abstract Factories but my issue is I want the Factory to figure out the correct object to instantiate at runtime, but every implementation I see involves passing an enum or some other value to the constructor.
This is my current design
using System;
namespace FactoryTest.Jobs
{
public class ExchangeProvider1 : IExchangeProvider
{
public void Buy()
{
Console.WriteLine("Buying on Exchange1!");
}
}
}
using System;
namespace FactoryTest.Jobs
{
public class ExchangeProvider2 : IExchangeProvider
{
public void Buy()
{
Console.WriteLine("Buying on Exchange2");
}
}
}
public interface IExchangeFactory
{
}
public interface IExchangeProvider
{
void Buy();
}
public class ExchangeFactory : IExchangeFactory
{
public static IExchangeProvider CreateExchange<T>() where T : IExchangeProvider
{
return Activator.CreateInstance<T>();
}
public static IExchangeProvider CreateExchange(string exchangeName)
{
return (IExchangeProvider) Activator.CreateInstance<IExchangeProvider>();
}
}
The problem is that I'm trying to have the factory build the correct provider based on details the user fills out in a web form. On hitting create I want to the factory to instantiate the correct provider and run the correct logic. But with this implementation Im forced to do something like
var provider = ExchangeFactory.CreateExchange<Exchange1>();
When I really want to be able to get the Exchange Type from the user at runtime from the web form and pass it to the factory
//Receive IExchangeType from user submitting web form
var provider = ExchangeFactory.CreateExchange<IExchangeType>();
Is this possible? I'm wondering (or the correct solution), or if I'm on the right track but am definitely hindered by a gap in knowledge.
Generally you shouldn't tell the factory which concrete type to create. You should give it the information it needs to make that decision by itself. Now, I'm not saying that this can't be a 1:1 relationship, just that the caller shouldn't tell the factory to make a specific concrete type.
Imagine you have a Student object with a Grade property. You also have a factory which produces ISchool, and concrete implementations ElementarySchool, MiddleSchool, and HighSchool. Now you could have 3 methods: CreateElementarySchool(), CreateMiddleSchool() and CreateHighSchool(), but then the caller has to decide which one it wants.
A better approach is to have a method which uses some information to create the the school. For example: CreateSchoolForGrade(grade). Internally, the factory will have logic which works out which concrete type matches the grade.
In your case, if you have a set of 2 types to choose from on a webform, you could accept the type (let's say the options are Empire or Rebels). You could have an enum:
public enum Faction
{
Empire,
Rebels
}
and then a factory method:
public IFaction CreateFaction(Faction faction)
{
switch (faction)
{
case Faction.Empire:
return new EmpireFaction();
case Faction.Rebels:
return new RebelsFaction();
default:
throw new NotImplementedException();
}
}
Now, imagine that you retire EmpireFaction, replacing it with EmpireFactionV2. You only need to modify your factory, and the caller doesn't care:
public IFaction CreateFaction(Faction faction)
{
switch (faction)
{
case Faction.Empire:
return new EmpireFactionV2();
case Faction.Rebels:
return new RebelsFaction();
default:
throw new NotImplementedException();
}
}
As noted in the comments the other answer is a violation of O/C Principle (and a bit of Single Responsibility Principle (SRP)) of SOLID.
A more dynamic approach is to inject all instances of the exchange and pick the correct one. Bellow example is based on the class name (not full-qualifed name, but that cane easily be changed).
public interface IExchange
{
void Buy();
}
public class Exchange1 : IExchange
{
public void Buy() => Console.WriteLine("Buying on Exchange1");
}
public class Exchange2 : IExchange
{
public void Buy() => Console.WriteLine("Buying on Exchange2");
}
public interface IExchangeFactory
{
IExchange CreateExchange(string exchangeName);
}
// All exchanges are instantiated and injected
public class ExchangeFactory : IExchangeFactory
{
private readonly IEnumerable<IExchange> exchanges;
public ExchangeFactory(IEnumerable<IExchange> exchanges)
{
this.exchanges = exchanges ?? throw new ArgumentNullException(nameof(exchanges));
}
public IExchange CreateExchange(string exchangeName)
{
var exchange = exchanges.FirstOrDefault(e => e.GetType().Name == exchangeName);
if(exchange==null)
throw new ArgumentException($"No Exchange found for '{exchangeName}'.");
return exchange;
}
}
It can easily be extended by registering further implementation with the DI, w/o any code changes on the factory
service.AddScoped<IExchange, Exchange3>();
service.AddScoped<IExchange, Exchange4>();
In high performance scenarios (a couple of 1000 requests per second) where the injected services are scoped/transient or the memory/GC pressure on creating this extra instances is high, you can use the provider pattern to only create the exchange that's really required:
public interface IExchangeProvider
{
IExchange CreateExchange(string exchangeName);
}
public class Exchange1Provider : IExchangeProvider
{
public IExchange CreateExchange(string exchangeName)
{
if(exchangeName == nameof(Exchange1))
{
// new it, resolve it from DI, use activation whatever suits your need
return new Exchange1();
}
return null;
}
}
public class Exchange2Provider : IExchangeProvider
{
public IExchange CreateExchange(string exchangeName)
{
if (exchangeName == nameof(Exchange2))
{
// new it, resolve it from DI, use activation whatever suits your need
return new Exchange1();
}
return null;
}
}
public class LazyExchangeFactory : IExchangeFactory
{
private readonly IEnumerable<IExchangeProvider> exchangeProviders;
public LazyExchangeFactory(IEnumerable<IExchangeProvider> exchangeProviders)
{
this.exchangeProviders = exchangeProviders ?? throw new ArgumentNullException(nameof(exchangeProviders));
}
public IExchange CreateExchange(string exchangeName)
{
// This approach is lazy. The providers could be singletons etc. (avoids allocations)
// and new instance will only be created if the parameters are matching
foreach (IExchangeProvider provider in exchangeProviders)
{
IExchange exchange = provider.CreateExchange(exchangeName);
// if the provider couldn't find a matcing exchange, try next provider
if (exchange != null)
{
return exchange;
}
}
throw new ArgumentException($"No Exchange found for '{exchangeName}'.");
}
}
This approach is similar to the first, with the exception that you are extending it by adding new IExchangeProviders. Both approaches allow you to extend the exchanges w/o a change on ExchangeFactory (or in high performance scenarios LazyExchangeFactory)
I've made a class with T. It looks like this.
public interface ISendLogic<T> where T : NarcoticsResult
{
ChangeType Change_New();
ChangeType Change_Cancel();
PurchaseType Purchase_New();
PurchaseType Purchase_Cancel();
}
public class SendLogic<T> : ISendLogic<T> where T : NarcoticsResult
{
private eReportType _type;
private bool Send_Change()
{
// Send to server by xml file
}
private bool Send_Purchase()
{
// Send to server by xml file
}
public ChangeType Change_New()
{
_type = change_new;
Send_Change();
}
public ChangeType Change_Cancel()
{
_type = change_cancel;
Send_Change();
}
public PurchaseType Purchase_New()
{
_type = purchase_new;
Send_Purchase();
}
public PurchaseType Purchase_Cancel()
{
_type = purchase_cancel;
Send_Purchase();
}
}
There are two types, ChangeType and PurchaseType
and these are inherited from NarcoticsResult.
I thought the person who want to use this class would use it like this.
// this class can only be used when someone wants to use change function
var logic = SendLogic<ChangeType >();
logic.Change_New();
logic.Change_Cancel();
Here is a question.
I want to force this class to be used only as I thought.
I mean, I want to prevent it to be used like this.
var logic = SendLogic<ChangeType>();
logic.Change_New(); // OK
logic.Purchase_New(); // You should make this class like SendLogic<PurchaseType>()
I thought I add some code which check type of T in every function.
How do you think the way I thought. I think there are better way to fix it
Please tell me a better way
thank you.
Personally, I don't think you need a generic class in this case. What you need is either an abstract base class or an interface. I personally love the interface approach as below:
public interface ISendLogic {
void New();
void Cancel();
}
So now you've got a contract that will force the consumer of your code to use New or Cancel methods only.
The next step you can implement that send logic interface for your specific implementation:
public class ChangeSendLogic : ISendLogic {
private eReportType _type;
public ChangeSendLogic(
/*you can put the necessary parameters in the constructor
and keep it as private fields in the object*/
)
{
}
private bool Send_Change()
{
// Send to server by xml file
}
public void New()
{
_type = change_new;
Send_Change();
}
public void Cancel()
{
_type = change_cancel;
Send_Change();
}
}
public class PurchaseSendLogic : ISendLogic {
private eReportType _type;
public PurchaseSendLogic(
/*you can put the necessary parameters in the constructor
and keep it as private fields in the object*/
)
{
}
private bool Send_Purchase()
{
// Send to server by xml file
}
public void New()
{
_type = change_new;
Send_Purchase();
}
public void Cancel()
{
_type = change_cancel;
Send_Purchase();
}
}
From here you can see those two classes handle the implementation for each type nicely. You can think this is as an implementation of single responsibility principle. So if you have one more type, you can just add one more implementation of this interface rather than updating the existing classes.
If you want to hide the creation of those objects, in the next part you can introduce a kind of factory or selector as below:
public enum SendLogicType {
Change,
Purchase
}
public static SendLogicSelector {
public static ISendLogic GetSendLogic(SendLogicType type)
{
switch(type)
{
case SendLogicType.Change:
return new ChangeSendLogic();
case SendLogicType.Purchase:
return new PurchaseSendLogic();
}
}
}
This is how the code will be consumed:
ISendLogic sendLogic = SendLogicSelector.GetSendLogic(SendLogicType.Change);
sendLogic.New(); // change new logic executed
sendLogic.Cancel(); // change cancel logic executed
sendLogic = SendLogicSelector.GetSendLogic(SendLogicType.Purchase);
sendLogic.New(); // purchase new logic executed
sendLogic.Cancel(); // purchase cancel logic executed
Hopefully, you can get the idea of my approach. Good luck! :)
Thank you for your comment
I divided it into two parts like below
public class ChangeSendLogic : SendLogic<ChangeType>, IChangeLogic
public class PurchaseSendLogic : SendLogic<PurchaseType>, IPurchaseLogic
And I also divided interface too
public interface IChangeLogic
{
ChangeType Change_New();
ChangeType Change_Cancel();
}
public interface IPurchaseLogic
{
PurchaseType Purchase_New();
PurchaseType Purchase_Cancel();
}
And I made SendLogic<T> class to abstract class.
This is because I want to make the person who wants to use this class to use a class that inherits from this class without directly accessing it.
Thank you for your comment. I got a good idea.
The following code is a valid C# construct that compile juste fine.
public class Weird : Weird.IWeird
{
private interface IWeird
{
}
}
What would be the possible uses of this?
Edit: This question is more specific that this one: "What is a private interface?". It shows that it's possible to implement a private interface from the parent type itself, which seems to be rather pointless. The only use I can think of would be a weird case of interface segregation where you would want to pass an instance of the parent class to a nested class instance as IWeird.
This is probably one of these situations in compiler development when prohibiting something has a higher cost than allowing it. Prohibiting this use would require writing and maintaining code to detect this situation, and report an error; if the feature works as-is, this is an additional work for the team, and it could be avoided. After all, perhaps someone with good imagination could figure out a way to use the feature.
As far as a useful example goes, one potential use is to make another implementation in the class, and use it as an alternative without exposing it to the users of the API:
public class Demo : Demo.Impl {
// Private interface
private interface Impl {
public bool IsValidState {get;}
void DoIt();
}
// Implementation for the error state
private class Error : Impl {
public bool IsValidState { get { return false; } }
public void DoIt() {
Console.WriteLine("Invalid state.");
}
}
private readonly string name;
// Implementation for the non-error state
public bool IsValidState { get { return true; } }
public void DoIt() {
Console.WriteLine("Hello, {0}", name);
}
// Constructor assigns impl depending on the parameter passed to it
private readonly Impl impl;
// Users are expected to use this method and property:
public bool IsValid {
get {
return impl.IsValidState;
}
}
public void SayHello() {
impl.DoIt();
}
// Constructor decides which impl to use
public Demo(string s) {
if (s == null) {
impl = new Error();
} else {
impl = this;
name = s;
}
}
}
As far as best practices go, this design is questionable at best. In particular, I would create a second nested class for the non-error implementation, rather than reusing the main class for that purpose. However, there is nothing terribly wrong with this design (apart from the fact that both IsValidState and DoIt are visible) so it was OK of the C# team to allow this use.
I am doing some research on design pattern implementation variants, i have come across and read some examples implemented here http://www.codeproject.com/Articles/37547/Exploring-Factory-Pattern and http://www.oodesign.com/factory-pattern.html. My focus of concern is when implementing factory pattern without reflection . the stated articles said that we need to register objects not classes which seems fine and logical to me but when seeing the implementation i see the duplication of objects e.g in the code below
// Factory pattern method to create the product
public IRoomType CreateProduct(RoomTypes Roomtype)
{
IRoomType room = null;
if (registeredProducts.Contains(Roomtype))
{
room = (IRoomType)registeredProducts[Roomtype];
room.createProduct();
}
if (room == null) { return room; }
else { return null; }
}
// implementation of concrete product
class NonACRoom : IRoomType
{
public static void RegisterProduct()
{
RoomFactory.Instance().RegisterProduct(new NonACRoom(), RoomTypes.NonAcRoom);
}
public void getDetails()
{
Console.WriteLine("I am an NON AC Room");
}
public IRoomType createProduct()
{
return new NonACRoom();
}
}
the method RegisterProduct is used for self registeration, we have to call it anyways before creating factory object i.e before some where in the main class of the client or anywhere applicable that ensure its calling. below is we are creating a new product and in the method above we are creating again a new product which seems non sense. any body comment on that
I have done something similar to this in the past. This is essentially what I came up with (and also doing away with the whole "Type" enumeration):
public interface ICreator
{
IPart Create();
}
public interface IPart
{
// Part interface methods
}
// a sample creator/part
public PositionPartCreator : ICreator
{
public IPart Create() { return new PositionPart(); }
}
public PositionPart : IPart
{
// implementation
}
Now we have the factory itself:
public sealed class PartFactory
{
private Dictionary<Type, IPartCreator> creators_ = new Dictionary<Type, IPartCreator>();
// registration (note, we use the type system!)
public void RegisterCreator<T>(IPartCreator creator) where T : IPart
{
creators_[typeof(T)] = creator;
}
public T CreatePart<T>() where T: IPart
{
if(creators_.ContainsKey(typeof(T))
return creators_[typeof(T)].Create();
return default(T);
}
}
This essentially does away with the need for a "type" enumeration, and makes things really easy to work with:
PartFactory factory = new PartFactory();
factory.RegisterCreator<PositionPart>(new PositionPartCreator());
// all your other registrations
// ... later
IPart p = factory.CreatePart<PositionPart>();
The first creation is used to give something to work on to RegisterProduct. Probably, the cost of that object is neglectable. It's done during initialization and won't matter much.
This instance is required though because in C# you need an object to call createProduct on. This is because you can't use reflection to store a reference to a type instead of a reference to an object.
What is the best way to implement polymorphic behavior in classes that I can't modify? I currently have some code like:
if(obj is ClassA) {
// ...
} else if(obj is ClassB) {
// ...
} else if ...
The obvious answer is to add a virtual method to the base class, but unfortunately the code is in a different assembly and I can't modify it. Is there a better way to handle this than the ugly and slow code above?
Hmmm... seems more suited to Adapter.
public interface ITheInterfaceYouNeed
{
void DoWhatYouWant();
}
public class MyA : ITheInterfaceYouNeed
{
protected ClassA _actualA;
public MyA( ClassA actualA )
{
_actualA = actualA;
}
public void DoWhatYouWant()
{
_actualA.DoWhatADoes();
}
}
public class MyB : ITheInterfaceYouNeed
{
protected ClassB _actualB;
public MyB( ClassB actualB )
{
_actualB = actualB;
}
public void DoWhatYouWant()
{
_actualB.DoWhatBDoes();
}
}
Seems like a lot of code, but it will make the client code a lot closer to what you want. Plus it'll give you a chance to think about what interface you're actually using.
Check out the Visitor pattern. This lets you come close to adding virtual methods to a class without changing the class. You need to use an extension method with a dynamic cast if the base class you're working with doesn't have a Visit method. Here's some sample code:
public class Main
{
public static void Example()
{
Base a = new GirlChild();
var v = new Visitor();
a.Visit(v);
}
}
static class Ext
{
public static void Visit(this object b, Visitor v)
{
((dynamic)v).Visit((dynamic)b);
}
}
public class Visitor
{
public void Visit(Base b)
{
throw new NotImplementedException();
}
public void Visit(BoyChild b)
{
Console.WriteLine("It's a boy!");
}
public void Visit(GirlChild g)
{
Console.WriteLine("It's a girl!");
}
}
//Below this line are the classes you don't have to change.
public class Base
{
}
public class BoyChild : Base
{
}
public class GirlChild : Base
{
}
I would say that the standard approach here is to wrap the class you want to "inherit" as a protected instance variable and then emulate all the non-private members (method/properties/events/etc.) of the wrapped class in your container class. You can then mark this class and its appropiate members as virtual so that you can use standard polymorphism features with it.
Here's an example of what I mean. ClosedClass is the class contained in the assembly whose code to which you have no access.
public virtual class WrapperClass : IClosedClassInterface1, IClosedClassInterface2
{
protected ClosedClass object;
public ClosedClass()
{
object = new ClosedClass();
}
public void Method1()
{
object.Method1();
}
public void Method2()
{
object.Method2();
}
}
If whatever assembly you are referencing were designed well, then all the types/members that you might ever want to access would be marked appropiately (abstract, virtual, sealed), but indeed this is unfortunately not the case (sometimes you can even experienced this issue with the Base Class Library). In my opinion, the wrapper class is the way to go here. It does have its benefits (even when the class from which you want to derive is inheritable), namely removing/changing the modifier of methods you don't want the user of your class to have access to. The ReadOnlyCollection<T> in the BCL is a pretty good example of this.
Take a look at the Decorator pattern. Noldorin actually explained it without giving the name of the pattern.
Decorator is the way of extending behavior without inheriting. The only thing I would change in Noldorin's code is the fact that the constructor should receive an instance of the object you are decorating.
Extension methods provide an easy way to add additional method signatures to existing classes. This requires the 3.5 framework.
Create a static utility class and add something like this:
public static void DoSomething(this ClassA obj, int param1, string param2)
{
//do something
}
Add a reference to the utility class on the page, and this method will appear as a member of ClassA. You can overload existing methods or create new ones this way.