Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 6 years ago.
Improve this question
In the application I am developing I am facing a situation; I want to know if there is a design pattern for this. It's as follows
User is presented on a web interface with different algorithms for a process
User selection is stored in the database.
Now, the application should perform computations differently depending on the algorithm selected.
What is a good strategy to implement this? Right now what we are doing is -
Have a reference DB table which has all the algorithm types and the corresponding class names in code (eg. If quick sort algorithm then we store QuickSort). This has to be manually updated everytime a new algo comes
In the code, get the algorithm type and use reflection to instantiate the appropriate algorithm type. In C# we use code similar to below
System.Reflection.Assembly types = System.Reflection.Assembly.LoadFile(System.Reflection.Assembly.GetExecutingAssembly().Location.ToString());
foreach (Type t in types)
if (t.Name==classname)
createinstanceof(t)
//classnames is the list of all the class types that is loaded from reference table in DB.
My gut feeling is there should be a simpler/better way to do this as it seems a very standard problem. I know the strategy pattern - but what I want is to simplify and possibly remove manual tasks.
You can use Interface + Reflection to avoid storing algorithm names in database.
Create an Interface IMySortingAlgorithms as,
public interface IMySortingAlgorithms
{
string Name { get; }
string[] Sort(string[] input);
}
Now, write a Factory that uses reflection to get the sorting algorithm.
public static class MyAlgoFactory
{
private static Dictionary<string, IMySortingAlgorithms> m_dict;
/// <summary>
/// For all the assmeblies in the current application domain,
/// Get me the object of all the Types that implement IMySortingAlgorithms
/// </summary>
static MyAlgoFactory()
{
var type = typeof(IMySortingAlgorithms);
m_dict = AppDomain.CurrentDomain.GetAssemblies().
SelectMany(s => s.GetTypes()).
Where(p => {return type.IsAssignableFrom(p) && p != type;}).
Select(t=> Activator.CreateInstance(t) as IMySortingAlgorithms).
ToDictionary(i=> i.Name);
}
public static IMySortingAlgorithms GetSortingAlgo(string name)
{
return m_dict[name];
}
}
All your sorting algorithms can now implement this interface.
public class MySortingAlgo1 : IMySortingAlgorithms
{
#region IMySortingAlgorithms Members
public string Name
{
get { return "MySortingAlgo1"; }
}
public string[] Sort(string[] input)
{
throw new NotImplementedException();
}
#endregion
}
This way you need not add the class names to database whenever you create a new class for sorting.
Following is the non-Linq version of MyAlgoFactory
/// <summary>
/// For all the assmeblies in the current application domain,
/// Get me the object of all the Types that implement IMySortingAlgorithms
/// </summary>
static MyAlgoFactory()
{
m_dict = new Dictionary<string, IMySortingAlgorithms>();
var type = typeof(IMySortingAlgorithms);
foreach (Assembly asm in AppDomain.CurrentDomain.GetAssemblies())
{
foreach (Type p in asm.GetTypes())
{
if (type.IsAssignableFrom(p) && p != type)
{
IMySortingAlgorithms algo = Activator.CreateInstance(p)
as IMySortingAlgorithms;
m_dict[algo.Name] = algo;
}
}
}
}
Yeah, you're right, what you want is the Strategy pattern. What you really want to do, though, is define an interface which each of your algorithms uses that allows you to specify the parameters for your algorithm and which allows you to invoke each of them simply through the interface, instead of the ugly reflection process you describe in the question.
Use the Factory design and the Strategy design as follows
public interface ISorter {
// Prototype for your sort function goes here
}
public class QuickSorter implements ISorter {}
public class SorterFactory {
public ISorter getSorter( string sortType ) {
// Return the correct type of sorting algorithm
if ( sortType.equals( "QuickSort" ) ) {
return new QuickSorter();
}
}
}
Then you just lookup what the user selected in the database and pass that in as the parameter to the factory.
NOTE TO MOD: Don't edit Java code if you don't know the correct syntax, unless you thought that this was C#, either way is fine by me.
Related
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 2 years ago.
Improve this question
I have some code which iterates through all classes implementing an interface. This works fine, example code below:
// Interface
public interface ICommand
{
string name { get; }
}
// Test class implementing interface and overrides value
public class TestCommand : ICommand
{
public string name { get { return "test"; } }
}
// Get all types implementing ICommand; This works
IEnumerable<Type> _commands = AppDomain.CurrentDomain.GetAssemblies().SelectMany(x => x.GetTypes()).Where(t => t.GetInterfaces().Contains(typeof(ICommand)));
// Iterate through all classes implementing ICommand; This works as well
foreach (Type _type in _commands)
{
// _type is the type of the class, which implements ICommand
_type.GetInterface(nameof(ICommand)) // This returns the Type of the interface, if i print it in console "ICommand"
// Here I would like to access the "name" property of the type, but i don't know how
}
Now the question: As I said in the comment in the code: How can I "cast" the return value of _type.GetInterface(nameof(ICommand)) to the instance of the interface of the class, so i can access for example the name property of for example the TestCommand class?
I searched the web for hours now but sadly i could not find anything, that answers this
So, any help would be really appreciated!
If there are any important informations I missed, comment and i will edit this post
I think what you want to do is this (using IsAssignableFrom):
var commandTypes = AppDomain.CurrentDomain.GetAssemblies().SelectMany(assembly => assembly.GetTypes()).Where(t => typeof(ICommand).IsAssignableFrom(t))
To create an instance of an object you can then do something like this:
foreach (var type in commandTypes)
{
var commandObjectInstance = Activator.CreateInstance(type);
Console.WriteLine(commandObjectInstance.Name);
}
There is a lot of assumptions here about the classes always having a parameterless constructor.
Also, reflection, which is what is being used here, comes with some drawbacks, for example performance or that things happen at runtime instead of compile time, this is something you should look more, and try to understand if you want to search assemblies for types and/or dynamically creating instances of those types.
Without more background information on why you are taking this approach, i cant tell you if it is good or bad or if you should do something else, but there might be other approaches, even some that might not have much of a downside. In the right scenario what you are doing can also be perfectly valid.
If I understand what you are doing this should get you what you are looking for. This would depend on the classes that you are loading having a public parameterless constructor but basically you need an instance of the class that you are loading in order to access the name property defined on your interface.
foreach (Type _type in _commands)
{
// Here I would like to access the "name" property of the type, but i don't know how
ICommand _command = (ICommand)Activator.CreateInstance(_type);
Console.Out.WriteLine(_command.name);
}
So i got the solution with the help of #StevenWiliams and #JimWolff
For anyone who for some reason has the same problem, here is my udated code:
IEnumerable<Type> _commands = AppDomain.CurrentDomain.GetAssemblies().SelectMany(x => x.GetTypes()).Where(t => t.GetInterfaces().Contains(typeof(ICommand)));
foreach (Type _type in _commands)
{
ICommand _command = (ICommand)Activator.CreateInstance(_type);
Debug.Log("Name: " + _command.name);
}
The problem I faced was, that I forgot, that classes can have multiple instances and therefor i cant get the value of the class directly. Creating an instance fixes this problem.
Again, credits to #StevenWiliams and #JimWolff.
I'd like to discuss about the best approach (in C#) to instantiate an object based on an input string. Let me explain.
Let'say I have a base class:
public abstract class BaseCar
{
public asbtract int GetEngineID();
//Other stuff...
}
Then I have several implementations of this class, let's say:
public class SportCar : BaseCar
{
public override int GetEngine()
{
//Specific implementation
}
}
public class OtherCar: BaseCar
{
public override int GetEngine()
{
//Specific implementation
}
}
And so on...
What I'd like to do is to make a static CarFactory class which has a CreateCar method which accepts a string as a parameter and returns a BaseCar instance, depending on what string you give. The string would be a name of a child class.
For example, if I call CarFactory.CreateCar('SportCar') it should return a SportCar instance.
I know I could use a simple switch statement to check which car has been requested and create a new instance based on that but I don't like this approach for two reasons:
I plan to have a lot of child classes, hard-coding every case wouldn't be too easy to mantain
I plan to implement an inizialization procedure to also give some initial values to the objects I create (using Reflection), so mixing hard-coding and reflection doesn't seem to be a good idea for me.
What I was thinking about is to use the Assembly.CreateInstance from System.Reflection to create an instance of the specified class but since this is the first time I approach this problem, I don't know if there are better ways to do that. Is this a valid approach ?
Considering the input string will come from an XML file, is there a simplier method ? Maybe my issue is already handled in some .NET Assembly which I'm missing.
Here is what I came up with. A generic factory class that automatically registers all types that are a subclass of the given type, and allows you to instantiate them via their name. This is somewhat related to the approach shown in the Java SO question linked by #Achilles in the comments, only that there is no initialisation function associated with the type.
There is no need to maintain an enum/switch combination of all types. It should also be somewhat easily extendable to handle your proposed reflection based initialisation.
static class StringFactory<T> where T : class
{
static private Dictionary<string, Type> s_dKnownTypes = new Dictionary<string, Type>();
static StringFactory()
{
RegisterAll();
}
static private void RegisterAll()
{
var baseType = typeof(T);
foreach (var domainAssembly in AppDomain.CurrentDomain.GetAssemblies())
{
foreach (var type in domainAssembly.GetTypes()
.Where(t => t.IsSubclassOf(baseType)))
{
s_dKnownTypes.Add(type.Name, type);
}
}
}
static public T Create(string _sTypeName)
{
Type knownType;
if (s_dKnownTypes.TryGetValue(_sTypeName, out knownType))
{
return (T)Activator.CreateInstance(knownType);
}
throw new KeyNotFoundException();
}
}
Assuming the classes of your question exist, you would instantiate a specific car like this:
var car = StringFactory<BaseCar>.Create("SportsCar");
DoSomethingWith(car.EngineID());
Since your question was for a discussion about the best approaches, please consider this only one of them. I have not used this in a production environment, and it is entirely possible that it is the wrong approach to your specific situation. It works well enough to show the general principle, however, and should provide a starting point for further discussion.
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 8 years ago.
Improve this question
I have a program I'm writing that has a form with around 15 inputs that describe a type of machine that we make (model, length, width, height, motor type, color, etc). There are 12 different models of this machine so I have a sub class "machine" and then 12 separate classes that inherit the "machine class". In my form, one of the inputs the user selects is the model. I'm trying to figure out a way to pass the 15 items to the specific "model" class fields without having to type it out 12 times with a case/switch (based on which model is selected). Is there a way to pass the inputs to the parent class and then when you figure out which specific class you need to create, reference the data that was stored in the parent class? I hope that makes sense what I'm saying. I'm struggling with describing the situation. If I can provide any more info please let me know!!
Thanks!
I would suggest you to write an interface, let's say something like IMachineModel with the required methods/properties. Write as many classes as models you have and implement the previously created interface.
Provide in each concrete class the logic required. Then you only need to instantiate the suitable class and use its properties and methods implemented from the interface.
Quick Example:
public class FirstConcreteMachineModel : IMachineModel
{
public string Model { get; set; }
public void DoSomething()
{
Console.WriteLine("I am a machine of type 1");
}
}
public class SecondConcreteMachineModel : IMachineModel
{
public string Model { get; set; }
public void DoSomething()
{
Console.WriteLine("I am a machine of type 2");
}
}
public class MachineModelFactory
{
public static IMachineModel CreateMachineModel(string type)
{
//switch with all possible types
switch (type)
{
case "one":
return new FirstConcreteMachineModel { Model = type };
case "two":
return new SecondConcreteMachineModel { Model = type };
default:
throw new ArgumentException("Machine type not supported");
}
}
}
Then you can use it like:
IMachineModel machine = MachineModelFactory.CreateMachineModel("two");
machine.DoSomething();
It would print
I am a machine of type 2.
To add to Areks's answer -- you could create a factory that given the inputs returns a class that implements IMachineModel .... Internally you have a number of options of how to determine the concrete class including your switch statement or chain of responsibility
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 4 years ago.
Improve this question
I started designing a small application and have some architecture-related questions.
I have some basic entities, which I'm willing to model - Repository and Indicator.
Repository is basically a facade using the Repository Pattern, which is able to retrieve / store arbitrary entities using some database holder (right now it's NHibernate-driven, but I guess that's not actually important).
The Indicator may be called the logical core of my application. It is used to combine abstract values and the exact time at which that value was achieved (so it forms and operates on Value - Time pairs).
I am willing to make this Indicator as generic as possible, still I think my current solution is a big fail :)
See the following chunks of code:
public interface IIndicator<T>
{
IEnumerable<T> RetrieveValues(DateTime start, DateTime end);
}
// Should also have something like indicator wrapper / proxy stub here - anything
// that represents the 'IIndicator' interface acts through that proxy and
// caches the evaluated data using it.
This is a basic attempt to implement the indicator (right now this can actually be considered as a mock):
public class Indicator<TValue> :
// Self-referencing generic parameter.
IIndicator<Indicator<TValue>.TimestampProxy>
{
// Proxy, which is used to add the timestamp to
// every indicated value.
public class TimestampProxy
{
public TValue Value;
public DateTime Time;
public TimestampProxy(DateTime time, TValue value)
{
Time = time;
Value = value;
}
}
private readonly IRepository repository;
public Indicator(IRepository repository)
{
this.repository = repository;
}
public IEnumerable<TimestampProxy> RetrieveValues(DateTime start, DateTime end)
{
// Note the custom time stamp comparation in the lambda
// expression. Comparation includes the 'start' and 'end' limits.
IQueryable<TimestampProxy> queryable = repository.Retrieve<TimestampProxy>(
x => x.Time.CompareTo(start) >= 0 && x.Time.CompareTo(end) <= 0);
return queryable.ToList();
}
}
Now - this might look fine, but I'm absolutely sure that the TimestampProxy used is really evil.
It also makes the things hard to understand (for example, method signature IEnumerable<TimestampProxy> RetrieveValues(...) would probably result in a "wtf?!" phrase from a person who examines the code).
Unfortunately, I can't come up with a better solution / global redesign - could you advice me how to do it or simply tell some ideas about how this kind of feature should be done?
Thanks.
How about refactoring the RetrieveValues method back into the Repository itself and going with a much simpler Indicator class that basically replaces your TimestampProxy class.
public class Indicator<T>
{
public DateTime Timestamp { get; set; }
public T Value { get; set; }
}
public class Repository
{
public IEnumerable<Indicator<T>> RetrieveIndicators<T>( DateTime start, DateTime end )
{
// determine table to query based on type T
// query and convert objects to Indicator<T>
// return collection
}
}
One thing that bothers me is that in making it generic you've lost the connection to the DB table. It might be better to simply define an interface that all of your specific DB objects implement and use partial implementations to map the actual "value" onto the Value property.
public interface Indicator<T>
{
DateTime Timestamp { get; }
T Value { get; }
}
public partial class TemperatureIndicator : Indicator<double>
{
public double Value { get { return this.Temperature; } }
}
Now have your repository implement methods that return objects of each type -- which can be used as (in .NET 4 or cast to in lower versions) objects of the interface type for common operations.
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 4 months ago.
Improve this question
I'm not talking about generic classes that declare properties or fields with the type of a generic parameter. I'm talking about generic properties which could be applied to both generic and non-generic classes.
I'm not talking about this:
public class Base<T>
{
public T BaseProperty { get; set; }
}
I'm talking about this:
public class Base
{
public T BaseProperty<T>
{
get
{
// Insert magic
}
set
{
// Insert magic
}
}
}
Or this:
public class Base<U>
{
public T BaseProperty<T>
{
get
{
// Insert magic
}
set
{
// Insert magic
}
}
public U OtherBaseProperty { get; set; }
}
The usage would go something like this:
var b = new Base();
b.BaseProperty<int> = 42;
int i = b.BaseProperty<int>;
b.BaseProperty<string> = "Hi";
string s = b.BaseProperty<string>;
Or for the second example:
var b = new Base<string>();
b.BaseProperty<int> = 42;
int i = b.BaseProperty<int>;
b.OtherBaseProperty = "Hi";
string s = b.OtherBaseProperty;
The // Insert Magic refers to handling each call to the generic property getter or setter that has a different type for the type parameter.
For example this:
b.BaseProperty<int> = 42;
Needs to be handled differently to:
b.BaseProperty<string> = "Hi";
I would envisage that for each type T if the getter is called before the setter is called then default(T) is returned.
When the setter is called the value is stored per type T so that when the getter is subsequently called the previous value that was set for that type is returned.
Note that under the covers properties are just methods.
Do you think this would be useful?
I've had a couple of times where I would have liked the ability to do this, yes.
However, the syntax involved would be pretty ugly, and it's sufficiently rarely useful that I think I prefer to just suck it up and go with generic methods.
No .
Without a killer use case, no. You can already achieve the same thing with a pair of generic methods, should you need it.
No.
Generic methods make sense, because they embody some (generic) operation that can sensibly be applied to different types.
But properties only make sense as uniquely named values with definite content. 'Generic properties', like you suggest, really only amounts to like-named properties with different signature and different content.
Here's one example where it would have been handy for me, if it would have been possible.
var settings = new Settings();
int timeout = settings<int>["CacheInMinutes"];
Where Settings loads an XML file of configuration variables.
That, compared to:
var settings = new Settings();
int timeout = int.Parse(settings["CacheInMinutes"]);
Really not much of a difference, but hey, I still would have preferred the generic indexer.
well, I have the situation that need generic property in non-generic class.
Example you have IComponent class that want to provide its parent IContainer with property Parent, since the component can belong to any container type. so you need to provide generic property rather than generic method
Component c = new Component();
Container p = new Container();
p.Add(c);
and then you access its parent using generic property (not aplicable now)
c.Parent.ContainerProperty;
c.Parent.ContainerMethod();
rather using verbose method like
c.Parent().ContainerProperty;
c.Parent().ContainerMethod();
Well, in this case generic property is more beautiful and make sense, since you don't need to input any argument.
If for some bizarre reason you decided you wanted it, you could sort of fake it with methods:
public class Thing
{
Dictionary<Type, object> xDict = new Dictionary<Type,object>();
public void set_X<T>(T x)
{
xDict[typeof(T)] = x;
}
public T get_X<T>()
{
return (T)xDict[typeof(T)];
}
}
Why you would want to is an entirely different matter, though. It generally makes more sense to start with something you want to do than some way you want to do it.