Properties
 

属性是成员变量和成员过程的特殊组合。它们提供了通过正常查看的赋值或成员访问来设置或检索对象的值的方法,但是如果需要更新自身,则还允许对象执行操作。

基本属性
声明和使用setter和getter属性。
索引属性
具有附加参数的属性。

基本属性


声明类似于会员程序的资源,但使用属性关键字而不是SubFunction.例如,让我们考虑窗口系统或GUI库的窗口类。

Type Window
Private:
    As String title_
End Type

Dim As Window w


为了设置窗口的标题,可以添加setter 属性:

Type Window
    Declare Property title(ByRef s As String)
Private:
    As String title_
End Type

Property Window.title(ByRef s As String)
    this.title_ = s
End Property

Dim As Window w
w.title = "My Window"


它与成员非常相似,因为它需要参数并根据参数将对象更新为新状态。但是,发送此参数的语法是基本赋值,而不是函数调用。通过将新值赋值给title属性,属性过程将自动使用给定的新值进行调用,并可更新窗口以反映更改。对象如何在内部表示属性状态。

通过设计,属性一次只能赋值一个值,因此属性过程不能有多个参数。

设置窗口标题后,也可以检索它。以下是添加getter 属性的方法:

Type Window
    '' setter
    Declare Property title(ByRef s As String)
    '' getter
    Declare Property title() As String
Private:
    As String title_
End Type

'' setter
Property Window.title(ByRef s As String)
    this.title_ = s
End Property

'' getter
Property Window.title() As String
    Return this.title_
End Property

Dim As Window w
w.title = "My Window"
Print w.title


吸气剂非常类似于功能.它应该返回属性的当前值,并且允许当前值根据需要从其他内部值计算。请注意,setter getter 使用相同的标识符,表示它们处理相同的属性。

就像方法重载一样,可以指定多个设置器,前提是它们具有不同的参数类型:

Type Window
    Declare Property title(ByRef s As String)
    Declare Property title(ByVal i As Integer)
    Declare Property title() As String
Private:
    As String title_
End Type

Property Window.title(ByRef s As String)
    this.title_ = s
End Property

Property Window.title(ByVal i As Integer)
    this.title_ = "Number: " & i
End Property

Property Window.title() As String
    Return this.title_
End Property

Dim As Window w
w.title = "My Window"
Print w.title
w.title = 5
Print w.title


与这个属性的例子相比,这里是不使用属性的类似的代码:

Type Window
    Declare Sub set_title(ByRef s As String)
    Declare Sub set_title(ByVal i As Integer)
    Declare Function get_title() As String
Private:
    As String title
End Type

Sub Window.set_title(ByRef s As String)
    this.title = s
End Sub

Sub Window.set_title(ByVal i As Integer)
    this.title = "Number: " & i
End Sub

Function Window.get_title() As String
    Return this.title
End Function

Dim As Window w
w.set_title("My Window")
Print w.get_title()
w.set_title(5)
Print w.get_title()


代码基本相同,只有语法不同。属性专门设计用于将setter / getter概念和语言的正常方法(赋值访问)的值组合到一个类的成员变量中。程序员可以决定他们喜欢哪种方式。

这是一个示例,演示文本用户界面窗口类,允许使用属性设置位置和标题:

Namespace tui
    Type Point
        Dim As Integer x, y
    End Type

    Type char
        Dim As UByte value
        Dim As UByte Color
    End Type

    Type Window
        '' public
        Declare Constructor _
            ( _
                x As Integer = 1, y As Integer = 1, _
                w As Integer = 20, h As Integer = 5, _
                title As ZString Ptr = 0 _
            )
        
        Declare Destructor

        Declare Sub show

        '' title property
        Declare Property title As String
        Declare Property title( new_title As String )

        '' position properties
        Declare Property x As Integer
        Declare Property x( new_x As Integer )

        Declare Property y As Integer
        Declare Property y( new_y As Integer )

    Private:
        Declare Sub redraw
        Declare Sub remove
        Declare Sub drawtitle

        Dim As String p_title
        Dim As Point Pos
        Dim As Point siz
    End Type

    Constructor Window _
        ( _
            x_ As Integer, y_ As Integer, _
            w_ As Integer, h_ As Integer, _
            title_ As ZString Ptr _
        )

        pos.x = x_
        pos.y = y_
        siz.x = w_
        siz.y = h_

        If( title_ = 0 ) Then
            title_ = @"untitled"
        End If

        p_title = *title_
    End Constructor

    Destructor Window
        Color 7, 0
        Cls
    End Destructor

    Property window.title As String
        title = p_title
    End Property

    Property window.title( new_title As String )
        p_title = new_title
        drawtitle
    End Property

    Property window.x As Integer
        Return pos.x
    End Property

    Property window.x( new_x As Integer )
        remove
        pos.x = new_x
        redraw
    End Property

    Property window.y As Integer
        Property = pos.y
    End Property

    Property window.y( new_y As Integer )
        remove
        pos.y = new_y
        redraw
    End Property

    Sub window.show
        redraw
    End Sub

    Sub window.drawtitle
        Locate pos.y, pos.x
        Color 15, 1
        Print Space( siz.x );
        Locate pos.y, pos.x + (siz.x \ 2) - (Len( p_title ) \ 2)
        Print p_title;
    End Sub

    Sub window.remove
        Color 0, 0
        Var sp = Space( siz.x )
        For i As Integer = pos.y To pos.y + siz.y - 1
            Locate i, pos.x
            Print sp;
        Next
    End Sub

    Sub window.redraw
        drawtitle
        Color 8, 7
        Var sp = Space( siz.x )
        For i As Integer = pos.y + 1 To pos.y + siz.y - 1
            Locate i, pos.x
            Print sp;
        Next
    End Sub
End Namespace

Dim win As tui.window = tui.window( 3, 5, 50, 15 )

win.show
Sleep 500

win.title = "Window 1"
Sleep 250
win.x = win.x + 10
Sleep 250

win.title = "Window 2"
Sleep 250
win.y = win.y - 2
Sleep 250

Locate 25, 1
Color 7, 0
Print "Press any key...";

Sleep


请注意,如何更新窗口的位置或标题自动导致重新绘制窗口。

索引属性


属性可以有一个称为index的附加参数(目前只允许一个附加参数)。索引在属性名称后面的括号中指定,就像该属性是一个数组(只有一个维度)一样。例如:

Type IntArray
    '' setters
    Declare Property value(index As Integer, v As Integer)
    Declare Property value(index As String, v As Integer)
    Declare Property value(index As Integer, v As String)
    Declare Property value(index As String, v As String)

    '' getters
    Declare Property value(index As Integer) As Integer
    Declare Property value(index As String) As Integer

Private:
    Dim As Integer data_(0 To 9)
End Type

Property IntArray.value(index As Integer) As Integer
    Return This.data_(index)
End Property

Property IntArray.value(index As String) As Integer
    Return This.data_(CInt(index))
End Property

Property IntArray.value(index As Integer, v As Integer)
    This.data_(index) = v
End Property

Property IntArray.value(index As String, v As Integer)
    This.data_(CInt(index)) = v
End Property

Property IntArray.value(index As Integer, v As String)
    This.data_(index) = CInt(v)
End Property

Property IntArray.value(index As String, v As String)
    This.data_(CInt(index)) = CInt(v)
End Property

Dim a As IntArray

a.value(0) = 1234
a.value("1") = 5678
a.value(2) = "-1234"
a.value("3") = "-5678"

Print a.value(0)
Print a.value("1")
Print a.value(2)
Print a.value("3")

Sleep

这将模拟可以赋值字符串的整数数组,甚至使用字符串进行索引。另请参见KeyPgProperty。