Coffeehouse Thread

5 posts

Forum Read Only

This forum has been made read only by the site admins. No new threads or comments can be added.

Extension properties?

Back to Forum: Coffeehouse
  • User profile image
    Sven Groot

    Ok, so we all know C# 3.0 and VB 9.0 will get extension methods. And we probably also all know that they won't get extension properties. The official explanation for this is that they haven't yet figured out a good syntax for this. Fair enough, it's not a major issue.

    However, I was tinkering around with XML literals in VB9 (as research for a blog post) , and noticed something very peculiar. One part of VB's new XML stuff is the ability to query an XML document, like this:
    elt.<Foo>.Value

    This get the <Foo> child elements of whatever element the "elt" variable was referring to, and then gets the content of the first <Foo> element as a string. To be clear, elt.<Foo> returns an IEnumerable(Of XElement), so Value is an extension on IEnumerable. Except that according to IntelliSense, it's an extension property.

    WTF? So I set out to investigate further. The above expression in VB would look like this in C# (which doesn't have this syntax): "elt.Elements("Foo").Value". Except it turns out that this Value property doesn't exist in C# (so we actually have to write "elt.Elements("Foo").First().Value" to get the same effect1). So it's a VB only thing. Curious, I look at Reflector. It turns out that the call to Value ends up looking like this:
    "InternalXmlHelper.get_Value(elt.Elements(XName.Get("Foo"))"

    InternalXmlHelper is an internal class in the application assembly itself (it's not in a library), and according to reflector it has a Value property like this:
    <Extension> _
    Public Shared Property Value(ByVal source As IEnumerable(Of XElement)) As String
        Get
            Dim item As XElement
            For Each item In source
                Return item.Value
            Next
            Return Nothing
        End Get
        Set(ByVal value As String)
            Dim item As XElement
            For Each item In source
                item.Value = value
                Exit For
            Next
        End Set
    End Property

    That, unfortunately, is impossible code. The <Extension> attribute cannot be applied to properties. If I paste this code into a VB source file it will not compile.

    And this seems strange to me. Visual Basic is much looser with parametrized properties than C# (the above, minus the <Extension> attribute, is perfectly valid), so at least for VB it seems that the above syntax should be fine for extension properties. In C# it'd be more complicated, but if the VB compiler is allowed to emit code like this, why can't we write it ourselves, at least in VB? Maybe it's because C#, which limits properties with parameters to indexers only, could not easily consume such an extension property if it were in a library? Even if that's the case, why not allow it but warn that it's not CLS compliant?

    Any thoughts?

    1 Actually not entirely the same effect, as the Value extension property in VB will return Nothing (null) if no child element <Foo> exists, whereas First() would throw an exception; FirstOrDefault() also doesn't help because then you get a NullReferenceException when trying to access the Value property.

  • User profile image
    Chadk

    Public Shared Property Value(ByVal source As IEnumerable(Of XElement)) As String Extends MyClass

    End Property

  • User profile image
    Sven Groot

    Chadk wrote:
    Public Shared Property Value(ByVal source As IEnumerable(Of XElement)) As String Extends MyClass

    End Property

    What is that supposed to do? Beta 2 doesn't accept it.

    It would be a better syntax for extension methods than what VB currently has. Is this planned? If so, got a link?

  • User profile image
    Chadk

    Sven Groot wrote:
    
    Chadk wrote:
    Public Shared Property Value(ByVal source As IEnumerable(Of XElement)) As String Extends MyClass

    End Property

    What is that supposed to do? Beta 2 doesn't accept it.

    It would be a better syntax for extension methods than what VB currently has. Is this planned? If so, got a link?

    IM SORry for my vague post. It was merely how i would like to see it.

  • User profile image
    JChung2006

    What does the IL look like for the InternalXmlHelper Value property?

    Is it possible that this is a Reflector bug?

    Perhaps Reflector takes the actual get_Value Function and set_Value Sub and converts them to Property syntax.  Like you said, that would be fine without the Extension() attribute but not so with the Extension() attribute, since it should not be possible to adorn a Shared property with that attribute.

Conversation locked

This conversation has been locked by the site admins. No new comments can be made.