首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Drawing.Rectangle的写入扩展

Drawing.Rectangle的写入扩展
EN

Stack Overflow用户
提问于 2018-10-01 22:49:27
回答 1查看 97关注 0票数 1

Drawing.Rectangle有这个方法

代码语言:javascript
复制
Dim r As Drawing.Rectangle = Drawing.Rectangle.FromLTRB(...)

我想编写一个类似于该函数的扩展方法。扩展方法将创建一个包含所有给定点的矩形。

我写过这样的方法,但是“矩形”没有注意到它有这个新方法。

当我尝试访问该方法时,Intellisense将找不到它。

我已经在这样的模块中声明了扩展:

代码语言:javascript
复制
<Extension()>
Public Function FromPoints(ByVal points As List(Of Drawing.Point)) As Drawing.Rectangle

    Dim leastX As Integer = 0
    Dim maxX As Integer = 0
    Dim leastY As Integer = 0
    Dim maxY As Integer = 0

    Dim bDone As Boolean = False

    For Each p As Point In points
        If Not bDone Then
            bDone = True
            leastX = p.X
            maxX = p.X
            leastY = p.Y
            maxY = p.Y
        Else
            If p.X < leastX Then
                leastX = p.X
            End If
            If p.X > maxX Then
                maxX = p.X
            End If
            If p.Y < leastY Then
                leastY = p.Y
            End If
            If p.Y > maxY Then
                maxY = p.Y
            End If
        End If
    Next

    Return Drawing.Rectangle.FromLTRB(leastX, leastY, maxX, maxY)

End Function

我错过了什么让它发挥作用的东西吗?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-10-02 00:17:22

引用的FromLTRB方法是Shared,即它是Rectangle类型的成员,而不是Rectangle实例的成员。注意,您在Rectangle上调用它,而在Rectangle上没有调用它。

只能像使用实例成员一样使用扩展方法。不能编写对Rectangle类型调用的扩展方法,而只能编写调用Rectangle实例的扩展方法。调用它的实例实际上由第一个参数表示。您的扩展方法必须如下所示:

代码语言:javascript
复制
Imports System.Runtime.CompilerServices

Public Module RectangleExtensions

    <Extension>
    Public Function FromPoints(source As Rectangle, points As List(Of Point)) As Rectangle
        '...
    End Function

End Module

然后你就得这样称呼它:

代码语言:javascript
复制
Dim rect As Rectangle
Dim points As New List(Of Point)

'...

Dim newRect = rect.FromPoints(points)

这并不理想,因为您必须首先使用一个Rectangle,但这是无法避免的,因为扩展方法需要调用扩展类型的实例。

顺便说一句,我倾向于写这样的方法:

代码语言:javascript
复制
Imports System.Runtime.CompilerServices

Public Module RectangleExtensions

    <Extension>
    Public Function FromPoints(source As Rectangle, points As IEnumerable(Of Point)) As Rectangle
        Dim pointArray = points.ToArray()
        Dim allX = pointArray.Select(Function(p) p.X).ToArray()
        Dim allY = pointArray.Select(Function(p) p.Y).ToArray()

        Return Rectangle.FromLTRB(allX.Min(),
                                  allY.Min(),
                                  allX.Max(),
                                  allY.Max())
    End Function

End Module

使用IEnumerable(Of Point)使该方法更加灵活,使用LINQ使其更加简洁。LINQ实际上会使性能更差,但是您必须有一个非常大的Points列表才能产生明显的差异。

编辑:

我应该明确地指出,扩展方法需要一个实例,而这个场景在调用该方法之前不需要一个实例,这意味着在本例中不应该使用扩展方法。只需编写一个获取Points列表并返回Rectangle的方法,并将其放在适当的位置:

代码语言:javascript
复制
Public Function RectangleFromPoints(points As IEnumerable(Of Point)) As Rectangle
    Dim pointArray = points.ToArray()
    Dim allX = pointArray.Select(Function(p) p.X).ToArray()
    Dim allY = pointArray.Select(Function(p) p.Y).ToArray()

    Return Rectangle.FromLTRB(allX.Min(),
                              allY.Min(),
                              allX.Max(),
                              allY.Max())
End Function
票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/52599906

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档