Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why are C# attributes so limited?

Tags:

c#

attributes

I understand that they are compile time, so they can't be generic, and must be initialized with constant values. But:
Why can't they have information you would get if you reflected whatever they are being applied to?
Why can't they accept lambda expressions, functions, or delegates? Aren't functions constant to the compiler?

Attributes could be a phenomenally powerful declarative tool if just one of the above were true, instead they are more like comments that can be read through reflection.

This was sort of a rant, but I really want to know why they seem like such a half assed feature.

Here is what I wanted to do. It was supposed to be an api for mapping values from resources through the function given to the attribute to the property the attribute is applied to. Note that the abstract class wouldn't have to exist if Attributes could know what they are reflecting. I'm posting this because someone wanted to know why I would want to give functions to attribute constructors, and maybe because what I'm trying to do has already been done.

public delegate void PropertyHandler(object parent, PropertyInfo property, object value);

[AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = true)]
public class FromResourceAttribute : Attribute
{
    private static readonly PropertyHandler m_defaultHandler =  (parent, property, value) => 
                                                                {
                                                                    property.SetValue(parent, value, null);
                                                                };

    public PropertyHandler Handler { get; set; }

    public FromResourceAttribute(PropertyHandler handler)
    {
        Handler = handler;
    }

    public FromResourceAttribute()
    {
        Handler = m_defaultHandler;
    }
}

public abstract class ResourceDependent
{
    public ResourceDependent(ResourceManager resources)
    {
        var resourceDependentProperties = 
            from property in GetType().GetProperties()
            let fromResourceAttributes = property.GetCustomAttributes(typeof(FromResourceAttribute), true)
            where fromResourceAttributes.Count() == 1
            let propertyHandler = ((FromResourceAttribute)fromResourceAttributes.Single()).Handler
            select new { Info = property, Handler = propertyHandler };

        foreach(var property in resourceDependentProperties)
        {
            property.Handler(this, property.Info, resources.GetObject(property.Info.Name));
        }
    }
}

class ResourceDependentTest : ResourceDependent
{
    [FromResource]
    public string Data { get; set; }

    [FromResource((parent, property, value) => property.SetValue(parent, ((string)value).Split('|'), null))]
    public string[] Data2 { get; set; }

    static PropertyHandler Data3Handler =   (parent, property, value) =>
                                            {
                                                //Magic
                                            };

    [FromResource(Data3Handler)]
    public int Data3 { get; set; }

    public ResourceDependentTest() : base(Properties.Resources.ResourceManager)
    {

    }
}
like image 324
cory Avatar asked Sep 20 '10 20:09

cory


People also ask

Why is C not A or B?

Because C comes after B The reason why the language was named “C” by its creator was that it came after B language. Back then, Bell Labs already had a programming language called “B” at their disposal.

Why C is a language?

As a middle-level language, C combines the features of both high-level and low-level languages. It can be used for low-level programming, such as scripting for drivers and kernels and it also supports functions of high-level programming languages, such as scripting for software applications etc.

Why are we still using C?

The C programming language doesn't seem to have an expiration date. It's closeness to the hardware, great portability and deterministic usage of resources makes it ideal for low level development for such things as operating system kernels and embedded software.

Why C is mostly used?

The C programming language is the recommended language for creating embedded system drivers and applications. The availability of machine-level hardware APIs, as well as the presence of C compilers, dynamic memory allocation, and deterministic resource consumption, make this language the most popular.


2 Answers

Why can't they have information you would get if you reflected whatever they are being applied to?

Part of the reason is attributes don't have to be applied to anything. It's perfectly legal to new up an attribute in imperative code which is not attached to anything.

// Not attached
var attrib = new CLSCompliantAttribute(false);

Why can't they accept lambda expressions, functions, or delegates? Aren't functions constant to the compiler?

All of these resolve down to the question of why delegates cannot be a part of an attribute. At their core delegates are made up of two parts 1) an instance and 2) a pointer to a method. #1 pretty much kills it as the instance is not constant and can't be a part of the attribute value.

There are several other case which exist with delegates including delegate's to static methods and expression trees. These have similar issues though in that all parts of the expression are not constant hence not encodable in an attribute value.

like image 197
JaredPar Avatar answered Dec 08 '22 12:12

JaredPar


Actually the question about why they can't be generic has been answered before, and according to Eric Lippert they are not supported simply because they'd add complexity to the language and it's just not been considered worth doing so far. It's certainly not because it's compile time. In IL you apparently can make generic attributes. (Reference.)

As for why they can't take lambda expressions and so forth, I imagine it's the same reason. The request for delegates to be used has been Microsoft Connect since 2006. You might vote for it if you like.

like image 32
Richard Anthony Freeman-Hein Avatar answered Dec 08 '22 13:12

Richard Anthony Freeman-Hein