当前位置:K88软件开发文章中心编程语言.NET.NET02 → 文章内容

Visual Basic 2010 新增功能

减小字体 增大字体 作者:佚名  来源:翔宇亭IT乐园  发布时间:2019-1-3 0:13:15

,下面是 Visual Basic 2005(不支持 lambda 表达式)中以前的代码的表示形式:

Dim query = Array.FindAll(customers, AddressOf Filter) 
 
  ... 
 
Function Filter(ByVal c As customer) As Boolean 
 Return c.Country = "Canada" 
End Function

  不幸的是,Visual Basic 2008 的 lambda 表达式要求表达式返回值,因此以下代码:

Array.ForEach(customers, Function(c) Console.WriteLine(c.Country))

  将会导致以下情况:

'Compile error: "Expression does not produce a value."

  Console.WriteLine 是一个 Sub 过程(C# 中为 void),因此它不会返回值,而这就是编译器产生错误的原因所在。为了处理此情况,Visual Basic 2010 引入了对语句 lambda 的支持,后者是包含一个或多个语句的 lambda:

Array.ForEach(customers, Sub(c) Console.WriteLine(c.Country))

  由于 Console.WriteLine 不返回值,因此我们可以只创建 Sub lambda,而不是 Function lambda。下面是使用多个语句的另一个示例:

Array.ForEach(customers, Sub(c) 
              Console.WriteLine("Country Name:") 
              Console.WriteLine(c.Country) 
             End Sub)

  当此代码运行时,它将为每个客户打印两行。另外请注意,如果在编码时悬停在 c 上,您将看到编译器会将类型推断为 Customer(键入 c As Customer 来显式声明类型也是合法的)。动态编写事件处理程序是语句 lambda 的另一个出色用途:

AddHandler b.Click, Sub(sender As Object, e As EventArgs) 
           MsgBox("Button Clicked") 
           'insert more complex logic here 
          End Sub

  并且,事实上,您可以将语句 lambda 与 Visual Basic 2008 中引入的一项功能(松散委托)结合使用。(可以使用委托 – 类型安全的函数指针 – 一次性执行多个函数。)这种组合将生成更为简单的签名:

AddHandler b.Click, Sub() 
           MsgBox("Button Clicked") 
           'insert more complex logic here 
          End Sub

  委托松散使您可以完全忽略事件处理程序中的参数 – 这是一个很好的优点,只要它们根本未使用过,因此它们只会在视觉上带来干扰。

  除了到目前为止我们已看到的单行 Sub lambda 和多行 Sub lambda 外,Visual Basic 2010 还支持多行 Function lambda:

Dim query = customers.Where(Function(c) 
               'Return only customers that have not been saved 
               'insert more complex logic here 
               Return c.ID = -1 
              End Function)

  语句 lambda 的另一个引人关注的方面是它们与 Visual Basic 2008 引入的匿名委托的相交方式。人们经常将这些委托与 C# 的匿名方法混淆,尽管严ge来说它们并不相同。当 Visual Basic 编译器基于 lambda 的方法签名推断委托类型时,将发生匿名委托:

Dim method = Function(product As String) 
        If product = "Paper" Then 
         Return 4.5 'units in stock 
        Else 
         Return 10 '10 of everything else 
        End If 
       End Function 
 
MsgBox(method("Paper"))

  如果运行此代码,您将看到消息框中显示值 4.5。此外,如果悬停在 method 上,您将看到文本 Dim method As <Function(String) As Double>。由于我们未提供实际委托类型,因此编译器将自动生成一个委托类型,如下所示:

Delegate Function $compilerGeneratedName$(product As String) As Double

  这称为匿名委托,因为它只会出现在编译器生成的代码中,而不会出现在编写的代码中。请注意,当事实上没有提供 As 子句来指定 lambda 的返回类型时,编译器将返回类型推断为 Double。编译器将查看 lambda 内的所有返回语句,并将确定类型 Double (4.5) 和 Integer (10):

'Notice the "As Single" 
Dim method = Function(product As String) As Single 
        If product = "Paper" Then 
         Return 4.5 'units in stock 
        Else 
         Return 10 '10 of everything else 
        End If 
       End Function

  然后,它将运行其基准类型算法,并确定它能够安全地将 10 转换为 Double,但无法安全地将 4.5 转换为 Integer;因此 Double 是更好的选择。

  您也可以显式控制返回类型,在这种情况下,编译器将不会尝试推断类型。非常常见的做法是将 lambda 赋给具有显式委托类型的变量,而不是依赖于编译器来推断委托类型:

Dim method As Func(Of String, Single) = 
 Function(product) 
  If product = "Paper" Then 
   Return 4.5 'units in stock 
  Else 
   Return 10 '10 of everything else 
  End If 
 End Function

  由于提供了显式目标类型,因此无需声明 As String 或 As Single;编译器可基于语句左边的委托类型来推断出其存在。因此,如果您悬停在 product 上,将会发现推断出的类型为 String。不再必须指定 As Single,因为委托类型已提供该信息。在前面的示例中,Func 委托(.NET Framework 包括该委托)的签名如下所示:

Delegate Function Func(Of T, R)(ByVal param As T) As R

  但有一个很小的例外之处,稍后我们将在“泛型方差”一节中看到。

  自动实现的属性

  在 Visual Basic 中,属性是用于向外部公开对象状态的类成员。典型的属性声明与如下声明类似:

Private _Country As String 
 
Property Country As String 
 Get 
  Return _Country 
 End Get 
 Set(ByVal value As String) 
  _Country = value 
 End Set 
End Property

  一个实际

上一页  [1] [2] [3] [4] [5]  下一页


Visual Basic 2010 新增功能