如何获得结构列表的总和?

时间:2013-12-13 10:24:28

标签: vb.net

我的结构定义如下: -

Public Structure MyStructure

    ' Some member variables and methods

    Public Shared Operator +(ByVal str1 As MyStructure, ByVal str2 As MyStructure) As MyStructure
        ' Some works
        Return New MyStructure (some parameters)
    End Operator

End Structure

我在列表中使用它: -

Dim my_list As List (Of MyStructure)
' code to fill in list

我想根据重载+运算符的定义计算列表中结构的总和;类似的东西: -

Dim my_sum As MyStructure = my_list.Sum(Function(x) x)

但这不起作用,因为返回类型不是double,single,integer,decimal,long或其中一个的可空版本。有没有办法在Sum方法中“获取”重载的+运算符?有些接口可以实现吗?

修改有人建议这可能与this question here重复。情况并非如此;该问题要求成员变量的总和;这个问题是要求重载+运算符定义的总和。

1 个答案:

答案 0 :(得分:1)

好吧这是冒险,但这是我的结果:

现有的Sum扩展仅提供基本类型作为结果,因此需要一个选择器。你找到了一个,好的。

现在我的下一步是编写我自己的扩展程序,以满足您的需求。

所以我正在寻找你所建议的内容,这个界面要求实现类拥有任何类型的运算符。 那没有。您也无法自己定义这样的界面,因为运算符本质上是静态的并且不能被覆盖。

所以下一步是通过一个泛型类型来扩展sum,它将自己约束为具有运算符的类型。

事实证明,你不能将泛型类型约束到结构。

所以这里是我工作的代码

据我了解你想做这样的事情:

Public Class MainClass
    ' ...
    Public Shared Sub Test()
        Dim lsta As New List(Of SomeClass)(New SomeClass() {
                                           New SomeClass(5, 10, 2.5),
                                           New SomeClass(7, 23, 1.2)
                                       }
                                   )
        Dim sum As SomeClass = lsta.Sum(Of SomeClass)()
    End Sub
    ' ...
End Class

现在你的结构必须是一个类,比如:

Public Class SomeClass
    Public Sub New(x As Int32, y As Int32, c As Double)
        m_iX = x
        m_iY = y
        m_fC = c
    End Sub
    Private m_iX As Int32
    Private m_iY As Int32
    Private m_fC As Double
    Public ReadOnly Property X
        Get
            Return m_iX
        End Get
    End Property
    Public ReadOnly Property Y
        Get
            Return m_iY
        End Get
    End Property
    Public ReadOnly Property C
        Get
            Return m_fC
        End Get
    End Property

    ' Custom operator:
    Public Shared Operator +(a As SomeClass, b As SomeClass) As SomeClass
        Return New SomeClass(a.X + b.X, a.Y + b.Y, a.C * b.C)
    End Operator

    ' This is coming in handy for initializing the first element in your sum
    Public Shared Function NeutralElement() As SomeClass
        Return New SomeClass(0, 0, 1)
    End Function
End Class

最后这里是扩展名:

Public Module ListExtension
    <Extension()> _
    Public Function Sum(Of T As SomeClass)(source As IEnumerable(Of SomeClass)) As SomeClass
        ' Note we have to constain T to SomeClass (also SomeClass cannot be a Structure :))
        Dim returnValue As T = SomeClass.NeutralElement()
        For Each el As T In source
            returnValue = returnValue + el
        Next
        Return returnValue
    End Function
End Module

我希望这清除了一些问题,提出任何问题,

......玩得很开心!