Estoy haciendo un parser para intercambiar los datos a/desde xml.
He definido un atributo y quiero pasar una funcion que convierta los valores de la variable que quiero guardar.
public class XmlableAttribute : Attribute
{
public string Name { get; private set; }
public Func<object, object> Converter { get; private set; }
public XmlableAttribute() : this("") { }
public XmlableAttribute(string Name)
{
this.Name = Name;
this.Converter = (v => v);
}
public XmlableAttribute(string Name, Func<object, object> ValueConverter)
{
this.Name = Name;
this.Converter = ValueConverter;
}
}
La idea es poder guardar el identificador y no el objeto en si, de esta manera:
[Xmlable("Transformacion", (t => (t as Transform2D).IdData)) ]
public Transform2D Transform { get; private set; }
El problema es que el compilador me dice: "Expression cannot contain anonymous methods or lambda expressions"
No entiendo por que no me deja hacerlo así, las funciones de Linq toman parametros Func<T,Q> con expresiones lambda sin problemas.
¿Alguna idea?
No está permitido por el lenguaje :(
http://ayende.com/Blog/archive/2006/05/12/CompilerWishListAttributesLambdaExpressions.aspx
Y el correspondiente issue en Connect:
https://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=91066&wa=wsignin1.0
Es del 2006, así que yo no tendría mucha fe en que lo vayan a cambiar... Pero en tu caso puedes usar alguno de los workarounds de Connect.
Se quedaba tan elegante... :(
Aunque no sirva de nada, la propuesta en connect ya tiene un voto mas.
Esos workarounds son muy feos.. :( [rabieta on] yo quiero pasar delegados a los atributos ya... [rabieta off]
A resignarse queda.
Como era un caso muy especifico, y por si alguien le sirve de algo, lo he resuelto asi:
[Xmlable("Transform", "IdData" )]
public Transform2D Transform { get; private set; }
public class XmlableAttribute : Attribute
{
public string Name { get; private set; }
public string Property { get; private set; }
public XmlableAttribute(string Name, string Property)
{
this.Name = Name;
this.Property = Property;
}
public XmlableAttribute() : this(null) { }
public XmlableAttribute(string Name)
{
this.Name = Name;
this.Property = null;
}
}
public class Xmlable
{
public static List<string> ToXml(object value)
{
List<string> xml = new List<string>();
PropertyInfo[] properties = value.GetType().GetProperties();
foreach (PropertyInfo p in properties)
{
object[] attributes = p.GetCustomAttributes(true);
foreach (object a in attributes)
{
if (a is XmlableAttribute)
{
object v = p.GetValue(value,null);
if ((a as XmlableAttribute).Property != null)
{
PropertyInfo i = v.GetType().GetProperty((a as XmlableAttribute).Property);
if (i != null)
{
v = i.GetValue(v, null);
}
}
xml.Add(string.Format("<{0} Type=\"{2}\">{1}</{0}>", p.Name, v.ToString(), p.PropertyType));
}
}
}
return xml;
}