I implemented an explicit conversion from string to object called Foo.
So => Foo f = (Foo)"foo data"; works
I need to implement a function that cast a string to the generic T, T in this case is Foo datatype.
public T Get<T>(object o){
// this always return false
if (typeof(T).IsAssignableFrom(typeof(String)))
{
// when i by pass the if above this throws invalid cast exception
return (T)(object)str;
}
return null;
}
// When I call this, it generated an error
// Invalid cast from 'System.String' to Foo
Foo myObj = Get<Foo>("another foo object");
// when I use the dynamic keyword it works but this is C# 4.0+ feature, my function is in the older framework
return (T)(dynamic)str;
An attribute cannot inherit from a generic class, nor can a generic class inherit from an attribute.
The where clause in a generic definition specifies constraints on the types that are used as arguments for type parameters in a generic type, method, delegate, or local function. Constraints can specify interfaces, base classes, or require a generic type to be a reference, value, or unmanaged type.
Generics are classes, structures, interfaces, and methods that have placeholders (type parameters) for one or more of the types that they store or use. A generic collection class might use a type parameter as a placeholder for the type of objects that it stores.
C# allows you to define generic classes, interfaces, abstract classes, fields, methods, static methods, properties, events, delegates, and operators using the type parameter and without the specific data type.
An example that uses Reflection:
class Program
{
static void Main(string[] args)
{
Foo myObj = TypeResolver.Get<Foo>("Foo data");
}
}
class TypeResolver
{
public static T Get<T>(object obj)
{
if (typeof(T).CanExplicitlyCastFrom<string>())
{
return obj.CastTo<T>();
}
return default(T);
}
}
public static class Extensions
{
public static bool CanExplicitlyCastFrom<T>(this Type type)
{
if (type == null)
throw new ArgumentNullException("type");
var paramType = typeof(T);
var castOperator = type.GetMethod("op_Explicit",
new[] { paramType });
if (castOperator == null)
return false;
var parametres = castOperator.GetParameters();
var paramtype = parametres[0];
if (paramtype.ParameterType == typeof(T))
return true;
else
return false;
}
public static T CastTo<T>(this object obj)
{
var castOperator = typeof(T).GetMethod("op_Explicit",
new[] { typeof(string) });
if (castOperator == null)
throw new InvalidCastException("Can't cast to " + typeof(T).Name);
return (T)castOperator.Invoke(null, new[] { obj });
}
}
Also take a look at this answer from @Jon Skeet - and specifically the quote about IsAssignableFrom
.
I don't think that's possible in a way that you envisioned it.
I'd suggest you put an 'interface contract' on your Foo classes - and then let generics do their work.
e.g. something like this - but this is just a fast solution I typed in...
class Factory
{
public static T Create<T, TVal>(TVal obj) where T : class, IFoo<TVal>, new()
{
return new T { Value = obj }; // return default(T);
}
}
interface IFoo<TVal>
{
TVal Value { get; set; }
}
class Foo : IFoo<string>
{
public string Value { get; set; }
public Foo() { }
}
// ...
public T Get<T, TVal>(TVal obj) where T : class, IFoo<TVal>, new()
{
return Factory.Create<T, TVal>(obj);
}
And you can call it in a similar way - providing that you have that luxury
- know the types etc.
(but you can work this out and adjust if needed)
Foo foo = Get<Foo, string>("another text");
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With