我已经学会了很多浏览Hidden Features of C#并且在我找不到的时候感到很惊讶 类似于VB.NET。
那么它的一些隐藏或鲜为人知的特征是什么?
答案 0 :(得分:128)
Exception When
条款在很大程度上是未知的。
考虑一下:
Public Sub Login(host as string, user as String, password as string, _
Optional bRetry as Boolean = False)
Try
ssh.Connect(host, user, password)
Catch ex as TimeoutException When Not bRetry
''//Try again, but only once.
Login(host, user, password, True)
Catch ex as TimeoutException
''//Log exception
End Try
End Sub
答案 1 :(得分:82)
Enum
s VB的一个真正的隐藏功能是completionlist
XML文档标记,可用于创建自己的Enum
类似扩展功能的类型。但是,此功能在C#中不起作用。
我最近的一个代码中的一个例子:
'
''' <completionlist cref="RuleTemplates"/>
Public Class Rule
Private ReadOnly m_Expression As String
Private ReadOnly m_Options As RegexOptions
Public Sub New(ByVal expression As String)
Me.New(expression, RegexOptions.None)
End Sub
Public Sub New(ByVal expression As String, ByVal options As RegexOptions)
m_Expression = expression
m_options = options
End Sub
Public ReadOnly Property Expression() As String
Get
Return m_Expression
End Get
End Property
Public ReadOnly Property Options() As RegexOptions
Get
Return m_Options
End Get
End Property
End Class
Public NotInheritable Class RuleTemplates
Public Shared ReadOnly Whitespace As New Rule("\s+")
Public Shared ReadOnly Identifier As New Rule("\w+")
Public Shared ReadOnly [String] As New Rule("""([^""]|"""")*""")
End Class
现在,在为声明为Rule
的变量赋值时,IDE会提供RuleTemplates
中可能值的智能感知列表。
由于这是一个依赖于IDE的功能,因此在使用它时很难显示它的外观,但我只是使用屏幕截图:
Completion list in action http://page.mi.fu-berlin.de/krudolph/stuff/completionlist.png
事实上,IntelliSense与使用Enum
时的完全相同。
答案 2 :(得分:49)
您是否注意到Like比较运算符?
Dim b As Boolean = "file.txt" Like "*.txt"
来自MSDN
的更多信息Dim testCheck As Boolean
' The following statement returns True (does "F" satisfy "F"?)'
testCheck = "F" Like "F"
' The following statement returns False for Option Compare Binary'
' and True for Option Compare Text (does "F" satisfy "f"?)'
testCheck = "F" Like "f"
' The following statement returns False (does "F" satisfy "FFF"?)'
testCheck = "F" Like "FFF"
' The following statement returns True (does "aBBBa" have an "a" at the'
' beginning, an "a" at the end, and any number of characters in '
' between?)'
testCheck = "aBBBa" Like "a*a"
' The following statement returns True (does "F" occur in the set of'
' characters from "A" through "Z"?)'
testCheck = "F" Like "[A-Z]"
' The following statement returns False (does "F" NOT occur in the '
' set of characters from "A" through "Z"?)'
testCheck = "F" Like "[!A-Z]"
' The following statement returns True (does "a2a" begin and end with'
' an "a" and have any single-digit number in between?)'
testCheck = "a2a" Like "a#a"
' The following statement returns True (does "aM5b" begin with an "a",'
' followed by any character from the set "L" through "P", followed'
' by any single-digit number, and end with any character NOT in'
' the character set "c" through "e"?)'
testCheck = "aM5b" Like "a[L-P]#[!c-e]"
' The following statement returns True (does "BAT123khg" begin with a'
' "B", followed by any single character, followed by a "T", and end'
' with zero or more characters of any type?)'
testCheck = "BAT123khg" Like "B?T*"
' The following statement returns False (does "CAT123khg" begin with'
' a "B", followed by any single character, followed by a "T", and'
' end with zero or more characters of any type?)'
testCheck = "CAT123khg" Like "B?T*"
答案 3 :(得分:48)
VB通过typedef
别名知道一种原始的Import
:
Imports S = System.String
Dim x As S = "Hello"
与泛型类型结合使用时更有用:
Imports StringPair = System.Collections.Generic.KeyValuePair(Of String, String)
答案 4 :(得分:45)
哦!不要忘记XML Literals。
Dim contact2 = _
<contact>
<name>Patrick Hines</name>
<%= From p In phoneNumbers2 _
Select <phone type=<%= p.Type %>><%= p.Number %></phone> _
%>
</contact>
答案 5 :(得分:39)
对象初始化也在那里!
Dim x as New MyClass With {.Prop1 = foo, .Prop2 = bar}
答案 6 :(得分:38)
DirectCast
DirectCast
是一个奇迹。从表面上看,它的工作方式类似于CType
运算符,因为它将对象从一种类型转换为另一种类型。但是,它的工作规则要严格得多。因此,CType
的实际行为通常是不透明的,并且根本不明显执行哪种转换。
DirectCast
仅支持两种不同的操作:
任何其他强制转换都不起作用(例如,尝试将Integer
拆箱到Double
)并导致编译时/运行时错误(取决于情况以及静态可以检测到的内容)类型检查)。因此,我尽可能使用DirectCast
,因为这最好地捕获了我的意图:根据情况,我要么取消已知类型的值或者执行向上转换。故事结束。
另一方面,使用CType
让代码的读者想知道程序员真正想要的是什么,因为它解析为各种不同的操作,包括调用用户定义的代码。
为什么这是一个隐藏的功能? VB团队发布了一个指南 1 ,它不鼓励使用DirectCast
(即使它实际上更快!),以使代码更加统一。我认为这是一个不好的指导方针,应该颠倒过来:尽可能支持DirectCast
而不是更普通的CType
运算符。它使代码更加清晰。另一方面,CType
只有在确实需要时才会被调用,即应该调用缩小的CType
运算符(参见operator overloading)。
1)我无法找到指南的链接,但我发现Paul Vick's take on it(VB团队的首席开发人员):
在现实世界中,你几乎不会注意到这种差异,所以你也可以选择CType,CInt等更灵活的转换运算符。
(Zack编辑:在此了解更多信息:How should I cast in VB.NET?)
答案 7 :(得分:37)
If
条件和合并运算符我不知道你怎么称呼它,但是Iif([表达式],[值如果为真],[值如果为假])作为对象函数可以计算。
它不像已弃用那么隐藏! VB 9有If
运算符,它更好,并且与C#的条件和合并运算符完全一样(取决于你想要的):
Dim x = If(a = b, c, d)
Dim hello As String = Nothing
Dim y = If(hello, "World")
编辑以显示另一个例子:
这适用于If()
,但会导致IIf()
Dim x = If(b<>0,a/b,0)
答案 8 :(得分:32)
这是一个很好的。 VB.Net中的Select Case语句非常强大。
当然有标准
Select Case Role
Case "Admin"
''//Do X
Case "Tester"
''//Do Y
Case "Developer"
''//Do Z
Case Else
''//Exception case
End Select
但还有更多......
你可以做范围:
Select Case Amount
Case Is < 0
''//What!!
Case 0 To 15
Shipping = 2.0
Case 16 To 59
Shipping = 5.87
Case Is > 59
Shipping = 12.50
Case Else
Shipping = 9.99
End Select
还有更多......
你可以(尽管可能不是一个好主意)对多个变量进行布尔检查:
Select Case True
Case a = b
''//Do X
Case a = c
''//Do Y
Case b = c
''//Do Z
Case Else
''//Exception case
End Select
答案 9 :(得分:31)
最简单的CSV解析器:
Microsoft.VisualBasic.FileIO.TextFieldParser
通过添加对Microsoft.VisualBasic的引用,可以在任何其他.Net语言中使用,例如C#
答案 10 :(得分:31)
我一直使用的主要节省时间是使用关键字:
With ReallyLongClassName
.Property1 = Value1
.Property2 = Value2
...
End With
我只是不喜欢打字而不是我必须!
答案 11 :(得分:26)
(编辑:在此处了解详情:Should I always use the AndAlso and OrElse operators?)
答案 12 :(得分:25)
方法中的静态成员。
例如:
Function CleanString(byval input As String) As String
Static pattern As New RegEx("...")
return pattern.Replace(input, "")
End Function
在上面的函数中,无论调用函数多少次,模式正则表达式都只会被创建一次。
另一个用途是保持“随机”的实例:
Function GetNextRandom() As Integer
Static r As New Random(getSeed())
Return r.Next()
End Function
此外,这与简单地将其声明为该类的共享成员不同;以这种方式声明的项目也保证是线程安全的。在这种情况下并不重要,因为表达式永远不会改变,但还有其他可能的地方。
答案 13 :(得分:25)
在vb中,这些运算符之间存在差异:
/
是Double
\
Integer
忽略余数
Sub Main()
Dim x = 9 / 5
Dim y = 9 \ 5
Console.WriteLine("item x of '{0}' equals to {1}", x.GetType.FullName, x)
Console.WriteLine("item y of '{0}' equals to {1}", y.GetType.FullName, y)
'Results:
'item x of 'System.Double' equals to 1.8
'item y of 'System.Int32' equals to 1
End Sub
答案 14 :(得分:23)
我非常喜欢Visual Basic 2005中引入的“我的”命名空间。我的是几组信息和功能的快捷方式。它提供对以下类型信息的快速直观访问:
答案 15 :(得分:23)
虽然很少有用,但事件处理可以大量定制:
Public Class ApplePie
Private ReadOnly m_BakedEvent As New List(Of EventHandler)()
Custom Event Baked As EventHandler
AddHandler(ByVal value As EventHandler)
Console.WriteLine("Adding a new subscriber: {0}", value.Method)
m_BakedEvent.Add(value)
End AddHandler
RemoveHandler(ByVal value As EventHandler)
Console.WriteLine("Removing subscriber: {0}", value.Method)
m_BakedEvent.Remove(value)
End RemoveHandler
RaiseEvent(ByVal sender As Object, ByVal e As EventArgs)
Console.WriteLine("{0} is raising an event.", sender)
For Each ev In m_BakedEvent
ev.Invoke(sender, e)
Next
End RaiseEvent
End Event
Public Sub Bake()
''// 1. Add ingredients
''// 2. Stir
''// 3. Put into oven (heated, not pre-heated!)
''// 4. Bake
RaiseEvent Baked(Me, EventArgs.Empty)
''// 5. Digest
End Sub
End Class
然后可以按以下方式测试:
Module Module1
Public Sub Foo(ByVal sender As Object, ByVal e As EventArgs)
Console.WriteLine("Hmm, freshly baked apple pie.")
End Sub
Sub Main()
Dim pie As New ApplePie()
AddHandler pie.Baked, AddressOf Foo
pie.Bake()
RemoveHandler pie.Baked, AddressOf Foo
End Sub
End Module
答案 16 :(得分:21)
我刚发现一篇文章谈论“!”运算符,也称为“字典查找运算符”。以下是文章摘录:http://panopticoncentral.net/articles/902.aspx
技术名称!操作者 是“字典查找运算符”。一个 dictionary是任何集合类型 由一个键而不是一个键索引 数字,就像那样的方式 英语词典中的条目是 用你想要的词索引 的定义。最常见的例子 字典类型是 System.Collections.Hashtable,其中 允许您添加(键,值)对 进入哈希表然后检索 使用键的值。例如, 以下代码添加了三个条目 到一个哈希表,看起来其中一个 使用关键“猪肉”。
Dim Table As Hashtable = New Hashtable
Table("Orange") = "A fruit"
Table("Broccoli") = "A vegetable"
Table("Pork") = "A meat"
Console.WriteLine(Table("Pork"))
!运算符可用于查找 来自任何字典类型的值 使用字符串索引其值。该 标识符之后!被用作 键查找操作。所以 以上代码可能已经 写成:
Dim Table As Hashtable = New Hashtable
Table!Orange = "A fruit"
Table!Broccoli = "A vegetable"
Table!Pork = "A meat"
Console.WriteLine(Table!Pork)
第二个例子是完全的 相当于第一个,但只是 看起来好多了,至少对我而言 眼睛。我发现有很多 哪里的地方!特别是可以使用 谈到XML和网络, 哪里只有吨 由索引编制的集合 串。一个不幸的限制是 事后跟着!仍然 必须是有效的标识符,所以如果 要用作键的字符串 有一些无效的标识符字符 在它,你不能使用!运营商。 (例如,你不能说 “表!AB $ CD = 5”,因为$不是 标识符合法。)在VB6和 之前,您可以使用括号 转义无效标识符(即 “表![AB $ CD]”),但是当我们开始时 使用括号来转义关键字,我们 失去了做到这一点的能力。多数情况 但是,这并不是太多 限制。
要获得真正的技术,x!y可以工作 x有一个默认属性,需要一个 String或Object作为参数。在 那种情况,x!y变成了 x.DefaultProperty( “Y”)。一个有趣的 旁注是有一个特殊的 规则的词汇语法 语言使这一切都有效。的! 字符也用作类型 语言中的字符和类型 在操作员之前吃掉字符。 因此,没有特殊规则,x!y会 扫描为“x!y”而不是“x! y“。幸运的是,因为没有 放在两个语言的地方 我们在一行中的标识符是有效的 刚刚介绍了规则,如果 之后的下一个角色!是个 我们考虑开始一个标识符 的!成为一个运营商,而不是一个类型 字符。
答案 17 :(得分:19)
这是内置的,并且比C#具有明显的优势。无需使用相同名称即可实现接口方法。
如:
Public Sub GetISCSIAdmInfo(ByRef xDoc As System.Xml.XmlDocument) Implements IUnix.GetISCSIInfo
End Sub
答案 18 :(得分:17)
强制ByVal
在VB中,如果将参数包装在一组额外的括号中,则可以覆盖方法的ByRef声明并将其转换为ByVal。例如,以下代码生成4,5,5而不是4,5,6
Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim R = 4
Trace.WriteLine(R)
Test(R)
Trace.WriteLine(R)
Test((R))
Trace.WriteLine(R)
End Sub
Private Sub Test(ByRef i As Integer)
i += 1
End Sub
请参阅Argument Not Being Modified by Procedure Call - Underlying Variable
答案 19 :(得分:16)
按名称传递参数,然后重新排序
Sub MyFunc(Optional msg as String= "", Optional displayOrder As integer = 0)
'Do stuff
End function
用法:
Module Module1
Sub Main()
MyFunc() 'No params specified
End Sub
End Module
也可以按任何顺序使用“:=”参数规范进行调用:
MyFunc(displayOrder:=10, msg:="mystring")
答案 20 :(得分:15)
自VB语句起,Using语句是新的,C#从一开始就拥有它。它会自动调用dispose。
E.g。
Using lockThis as New MyLocker(objToLock)
End Using
答案 21 :(得分:14)
考虑以下事件声明
Public Event SomethingHappened As EventHandler
在C#中,您可以使用以下语法检查事件订阅者:
if(SomethingHappened != null)
{
...
}
但是,VB.NET编译器不支持此功能。它实际上创建了一个隐藏的私有成员字段,该字段在IntelliSense中不可见:
If Not SomethingHappenedEvent Is Nothing OrElse SomethingHappenedEvent.GetInvocationList.Length = 0 Then
...
End If
更多信息:
http://jelle.druyts.net/2003/05/09/BehindTheScenesOfEventsInVBNET.aspx http://blogs.msdn.com/vbteam/archive/2009/09/25/testing-events-for-nothing-null-doug-rothaus.aspx
答案 22 :(得分:14)
如果您需要一个变量名称来匹配关键字的名称,请用括号括起来。不是。虽然是最好的做法 - 但它可以明智地使用。
e.g。
Class CodeException
Public [Error] as String
''...
End Class
''later
Dim e as new CodeException
e.Error = "Invalid Syntax"
e.g。评论示例(@Pondidum):
Class Timer
Public Sub Start()
''...
End Sub
Public Sub [Stop]()
''...
End Sub
答案 23 :(得分:14)
导入别名在很大程度上也是未知的:
Import winf = System.Windows.Forms
''Later
Dim x as winf.Form
答案 24 :(得分:13)
关于XML Literals有几个答案,但不是关于这个特定情况:
您可以使用XML Literals来包含原本需要转义的字符串文字。例如,包含双引号的字符串文字。
而不是:
Dim myString = _
"This string contains ""quotes"" and they're ugly."
你可以这样做:
Dim myString = _
<string>This string contains "quotes" and they're nice.</string>.Value
如果您正在测试CSV解析的文字,这将非常有用:
Dim csvTestYuck = _
"""Smith"", ""Bob"", ""123 Anywhere St"", ""Los Angeles"", ""CA"""
Dim csvTestMuchBetter = _
<string>"Smith", "Bob", "123 Anywhere St", "Los Angeles", "CA"</string>.Value
(当然,您不必使用<string>
标签;您可以使用您喜欢的任何标签。)
答案 25 :(得分:12)
可以使用#
围绕日期来初始化DateTimeDim independanceDay As DateTime = #7/4/1776#
您还可以使用类型推断和此语法
Dim independanceDay = #7/4/1776#
这比使用构造函数
好很多Dim independanceDay as DateTime = New DateTime(1776, 7, 4)
答案 26 :(得分:12)
您可以在一行中拥有2行代码。因此:
Dim x As New Something : x.CallAMethod
答案 27 :(得分:11)
可选参数
选项比创建新的重载要容易得多,例如:
Function CloseTheSystem(Optional ByVal msg AS String = "Shutting down the system...")
Console.Writeline(msg)
''//do stuff
End Function
答案 28 :(得分:9)
带参数的属性
我一直在做一些C#编程,并发现了一个缺少VB.Net的功能,但这里没有提到。
如何执行此操作(以及c#限制)的示例可在以下位置查看:Using the typical get set properties in C#... with parameters
我摘录了该答案的代码:
Private Shared m_Dictionary As IDictionary(Of String, Object) = _
New Dictionary(Of String, Object)
Public Shared Property DictionaryElement(ByVal Key As String) As Object
Get
If m_Dictionary.ContainsKey(Key) Then
Return m_Dictionary(Key)
Else
Return [String].Empty
End If
End Get
Set(ByVal value As Object)
If m_Dictionary.ContainsKey(Key) Then
m_Dictionary(Key) = value
Else
m_Dictionary.Add(Key, value)
End If
End Set
End Property
答案 29 :(得分:9)
使用语句堆叠/分组多个:
Dim sql As String = "StoredProcedureName"
Using cn As SqlConnection = getOpenConnection(), _
cmd As New SqlCommand(sql, cn), _
rdr As SqlDataReader = cmd.ExecuteReader()
While rdr.Read()
''// Do Something
End While
End Using
公平地说,你也可以用C#来做。但是很多人都不知道这两种语言。
答案 30 :(得分:9)
VB.Net中的标题案例可以通过旧的VB6 fxn实现:
StrConv(stringToTitleCase, VbStrConv.ProperCase,0) ''0 is localeID
答案 31 :(得分:8)
我发现其中一个非常有用且有助于解决许多错误的功能是将参数显式传递给函数,尤其是在使用可选项时。
以下是一个例子:
Public Function DoSomething(byval x as integer, optional y as boolean=True, optional z as boolean=False)
' ......
End Function
然后你可以这样称呼它:
DoSomething(x:=1, y:=false)
DoSomething(x:=2, z:=true)
or
DoSomething(x:=3,y:=false,z:=true)
这样更干净,没有bug,然后调用这个函数
DoSomething(1,true)
答案 32 :(得分:7)
你可以在一行中有一个If。
If True Then DoSomething()
答案 33 :(得分:7)
请注意when
Catch ex As IO.FileLoadException When attempt < 3
的使用情况
Do
Dim attempt As Integer
Try
''// something that might cause an error.
Catch ex As IO.FileLoadException When attempt < 3
If MsgBox("do again?", MsgBoxStyle.YesNo) = MsgBoxResult.No Then
Exit Do
End If
Catch ex As Exception
''// if any other error type occurs or the attempts are too many
MsgBox(ex.Message)
Exit Do
End Try
''// increment the attempt counter.
attempt += 1
Loop
最近在VbRad
中查看答案 34 :(得分:7)
如果你从来不知道以下内容,你真的不相信它是真的,这真的是C#缺乏时间的东西:
(它被称为XML文字)
Imports <xmlns:xs="System">
Module Module1
Sub Main()
Dim xml =
<root>
<customer id="345">
<name>John</name>
<age>17</age>
</customer>
<customer id="365">
<name>Doe</name>
<age>99</age>
</customer>
</root>
Dim id = 1
Dim name = "Beth"
DoIt(
<param>
<customer>
<id><%= id %></id>
<name><%= name %></name>
</customer>
</param>
)
Dim names = xml...<name>
For Each n In names
Console.WriteLine(n.Value)
Next
For Each customer In xml.<customer>
Console.WriteLine("{0}: {1}", customer.@id, customer.<age>.Value)
Next
Console.Read()
End Sub
Private Sub CreateClass()
Dim CustomerSchema =
XDocument.Load(CurDir() & "\customer.xsd")
Dim fields =
From field In CustomerSchema...<xs:element>
Where field.@type IsNot Nothing
Select
Name = field.@name,
Type = field.@type
Dim customer =
<customer> Public Class Customer
<%= From field In fields Select <f>
Private m_<%= field.Name %> As <%= GetVBPropType(field.Type) %></f>.Value %>
<%= From field In fields Select <p>
Public Property <%= field.Name %> As <%= GetVBPropType(field.Type) %>
Get
Return m_<%= field.Name %>
End Get
Set(ByVal value As <%= GetVBPropType(field.Type) %>)
m_<%= field.Name %> = value
End Set
End Property</p>.Value %>
End Class</customer>
My.Computer.FileSystem.WriteAllText("Customer.vb",
customer.Value,
False,
System.Text.Encoding.ASCII)
End Sub
Private Function GetVBPropType(ByVal xmlType As String) As String
Select Case xmlType
Case "xs:string"
Return "String"
Case "xs:int"
Return "Integer"
Case "xs:decimal"
Return "Decimal"
Case "xs:boolean"
Return "Boolean"
Case "xs:dateTime", "xs:date"
Return "Date"
Case Else
Return "'TODO: Define Type"
End Select
End Function
Private Sub DoIt(ByVal param As XElement)
Dim customers =
From customer In param...<customer>
Select New Customer With
{
.ID = customer.<id>.Value,
.FirstName = customer.<name>.Value
}
For Each c In customers
Console.WriteLine(c.ToString())
Next
End Sub
Private Class Customer
Public ID As Integer
Public FirstName As String
Public Overrides Function ToString() As String
Return <string>
ID : <%= Me.ID %>
Name : <%= Me.FirstName %>
</string>.Value
End Function
End Class
End Module
'Results:
ID : 1
Name : Beth
John
Doe
345: 17
365: 99
看看Beth Massi的XML Literals Tips/Tricks。
答案 35 :(得分:7)
答案 36 :(得分:6)
这是一个我从未见过的有趣的;我知道它在VS 2008中起作用,至少:
如果你不小心用分号结束你的VB行,因为你做了太多的C#,分号会被自动删除。实际上不可能(至少在VS 2008中)不小心用分号结束VB行。试试吧!
(这并不完美;如果您在最后一个班级名称的中途输入分号,则不会自动填写班级名称。)
答案 37 :(得分:6)
与VB中的C语言中的break
不同,您可以Exit
或Continue
您想要的块:
For i As Integer = 0 To 100
While True
Exit While
Select Case i
Case 1
Exit Select
Case 2
Exit For
Case 3
Exit While
Case Else
Exit Sub
End Select
Continue For
End While
Next
答案 38 :(得分:5)
在vb.net中声明数组时,始终使用“0到xx”语法。
Dim b(0 to 9) as byte 'Declares an array of 10 bytes
它清楚地表明了数组的范围。将它与等效的
进行比较Dim b(9) as byte 'Declares another array of 10 bytes
即使你知道第二个例子由10个元素组成,它也感觉不太明显。而且我不记得我从程序员那里看到代码的次数,而不是写了
Dim b(10) as byte 'Declares another array of 10 bytes
这当然是完全错误的。因为b(10)创建一个11字节的数组。并且它很容易导致错误,因为它看起来对任何不知道要寻找什么的人都是正确的。
“0到xx”语法也适用于下面的
Dim b As Byte() = New Byte(0 To 9) {} 'Another way to create a 10 byte array
ReDim b(0 to 9) 'Assigns a new 10 byte array to b
通过使用完整语法,您还将向将来阅读您的代码的任何人展示您知道自己在做什么。
答案 39 :(得分:5)
如果用[和]
括起名称,可以对属性和变量名使用保留关键字Public Class Item
Private Value As Integer
Public Sub New(ByVal value As Integer)
Me.Value = value
End Sub
Public ReadOnly Property [String]() As String
Get
Return Value
End Get
End Property
Public ReadOnly Property [Integer]() As Integer
Get
Return Value
End Get
End Property
Public ReadOnly Property [Boolean]() As Boolean
Get
Return Value
End Get
End Property
End Class
'Real examples:
Public Class PropertyException : Inherits Exception
Public Sub New(ByVal [property] As String)
Me.Property = [property]
End Sub
Private m_Property As String
Public Property [Property]() As String
Get
Return m_Property
End Get
Set(ByVal value As String)
m_Property = value
End Set
End Property
End Class
Public Enum LoginLevel
[Public] = 0
Account = 1
Admin = 2
[Default] = Account
End Enum
答案 40 :(得分:5)
IIf(False, MsgBox("msg1"), MsgBox("msg2"))
结果如何?两个消息框!!!! 发生这种情况时,IIf函数在到达函数时会计算两个参数。
VB有一个新的If运算符(就像C#?: operator):
If(False, MsgBox("msg1"), MsgBox("msg2"))
仅显示第二个msgbox。
一般情况下,我建议更换你的vb代码中的所有IIF,除非你想要它们两个项目:
Dim value = IIf(somthing, LoadAndGetValue1(), LoadAndGetValue2())
您可以确定两个值都已加载。
答案 41 :(得分:5)
与Parsa's答案类似,like operator有很多可以匹配的简单通配符。在阅读MSDN doco时,我几乎摔倒在椅子上:-)
答案 42 :(得分:5)
选择Case代替多个If / ElseIf / Else语句。
在此示例中假设简单的几何对象:
Function GetToString(obj as SimpleGeomertyClass) as String
Select Case True
Case TypeOf obj is PointClass
Return String.Format("Point: Position = {0}", _
DirectCast(obj,Point).ToString)
Case TypeOf obj is LineClass
Dim Line = DirectCast(obj,LineClass)
Return String.Format("Line: StartPosition = {0}, EndPosition = {1}", _
Line.StartPoint.ToString,Line.EndPoint.ToString)
Case TypeOf obj is CircleClass
Dim Line = DirectCast(obj,CircleClass)
Return String.Format("Circle: CenterPosition = {0}, Radius = {1}", _
Circle.CenterPoint.ToString,Circle.Radius)
Case Else
Return String.Format("Unhandled Type {0}",TypeName(obj))
End Select
End Function
答案 43 :(得分:5)
在VB8和前面的版本中,如果没有为引入的变量指定任何类型,则会自动检测对象类型。在VB9(2008)中,如果Option Infer设置为On(默认情况下),Dim
将像C#的var
关键字一样
答案 44 :(得分:4)
同样重要的是要记住,默认情况下,VB.NET项目的根命名空间是项目属性的一部分。默认情况下,此根命名空间将与项目具有相同的名称。使用命名空间块结构时,名称实际上附加到该根命名空间。例如:如果项目名为MyProject,那么我们可以将变量声明为:
Private obj As MyProject.MyNamespace.MyClass
要更改根命名空间,请使用项目 - &gt;属性菜单选项。也可以清除根命名空间,这意味着所有命名空间块都成为它们包含的代码的根级别。
答案 45 :(得分:4)
Nothing关键字可以表示默认值(T)或null,具体取决于上下文。你可以利用它来制作一个非常有趣的方法:
'''<summary>Returns true for reference types, false for struct types.</summary>'
Public Function IsReferenceType(Of T)() As Boolean
Return DirectCast(Nothing, T) Is Nothing
End Function
答案 46 :(得分:4)
与C#不同,在VB中,您可以依赖非可空项目的默认值:
Sub Main()
'Auto assigned to def value'
Dim i As Integer '0'
Dim dt As DateTime '#12:00:00 AM#'
Dim a As Date '#12:00:00 AM#'
Dim b As Boolean 'False'
Dim s = i.ToString 'valid
End Sub
而在C#中,这将是编译器错误:
int x;
var y = x.ToString(); //Use of unassigned value
答案 47 :(得分:4)
MyClass关键字提供了一种将类实例成员引用为最初实现的方法,忽略了任何派生类重写。
答案 48 :(得分:4)
可能是这个链接应该有帮助
http://blogs.msdn.com/vbteam/archive/2007/11/20/hidden-gems-in-visual-basic-2008-amanda-silver.aspx
答案 49 :(得分:3)
VB还提供了OnError语句。但是这些日子并没有多大用处。
On Error Resume Next
' Or'
On Error GoTo someline
On Error Resume Next
' Or'
On Error GoTo someline
答案 50 :(得分:3)
混淆名称空间
Imports Lan = Langauge
虽然不是VB.Net独有的,但在遇到命名空间冲突时经常会忘记它。
答案 51 :(得分:2)
Private Sub Button1_Click(ByVal sender As Button, ByVal e As System.EventArgs)
Handles Button1.Click
sender.Enabled = True
DisableButton(sender)
End Sub
Private Sub Disable(button As Object)
button.Enabled = false
End Sub
在这个片段中你有2个(可能更多?)你在C#中永远做不到的事情:
此外,在C#中你不能在对象上使用预期的功能 - 在C#中你可以梦想它(现在他们制作了动态关键字,但它远离VB)。 在C#中,如果你要写(new object())。启用你会得到一个错误,类型对象没有方法'Enabled'。 现在,如果这是安全的话,我不是那个会推荐你的人,信息是按原样提供的,你自己做的,公共汽车,有时候(比如使用COM对象时)这是一件好事。 当预期值肯定是一个按钮时,我个人总是写(发送者为按钮)。
实际上:以此为例:
Private Sub control_Click(ByVal sender As Control, ByVal e As System.EventArgs)
Handles TextBox1.Click, CheckBox1.Click, Button1.Click
sender.Text = "Got it?..."
End Sub
答案 52 :(得分:2)
不可能在VB中显式实现接口成员,但可以用不同的名称实现它们。
Interface I1
Sub Foo()
Sub TheFoo()
End Interface
Interface I2
Sub Foo()
Sub TheFoo()
End Interface
Class C
Implements I1, I2
Public Sub IAmFoo1() Implements I1.Foo
' Something happens here'
End Sub
Public Sub IAmFoo2() Implements I2.Foo
' Another thing happens here'
End Sub
Public Sub TheF() Implements I1.TheFoo, I2.TheFoo
' You shouldn't yell!'
End Sub
End Class
答案 53 :(得分:2)
您可以使用REM注释掉一行而不是' 。不是非常有用,但使用“!!!!!!!”帮助重要评论突出管他呢。
答案 54 :(得分:2)
Nullable(Of Date)
,这样我就可以保持日期无价值,接受存储过程中的默认值
<System.Diagnostics.DebuggerStepThrough> _
Protected Function GP(ByVal strName As String, ByVal dtValue As Date) As SqlParameter
Dim aParm As SqlParameter = New SqlParameter
Dim unDate As Date
With aParm
.ParameterName = strName
.Direction = ParameterDirection.Input
.SqlDbType = SqlDbType.SmallDateTime
If unDate = dtValue Then 'Unassigned variable
.Value = "1/1/1900 12:00:00 AM" 'give it a default which is accepted by smalldatetime
Else
.Value = CDate(dtValue.ToShortDateString)
End If
End With
Return aParm
End Function
<System.Diagnostics.DebuggerStepThrough()> _
Protected Function GP(ByVal strName As String, ByVal dtValue As Nullable(Of Date)) As SqlParameter
Dim aParm As SqlParameter = New SqlParameter
Dim unDate As Date
With aParm
.ParameterName = strName
.Direction = ParameterDirection.Input
.SqlDbType = SqlDbType.SmallDateTime
If dtValue.HasValue = False Then
'// it's nullable, so has no value
ElseIf unDate = dtValue.Value Then 'Unassigned variable
'// still, it's nullable for a reason, folks!
Else
.Value = CDate(dtValue.Value.ToShortDateString)
End If
End With
Return aParm
End Function
答案 55 :(得分:2)
我不知道你怎么称呼它,但If
运算符可以计算。
在某种程度上,它与许多类C语言中的?:
(三元组)或??
运算符非常相似。但是,重要的是要注意它确实评估了所有参数,因此重要的是不要传递任何可能导致异常的内容(除非你想要它)或任何可能导致意外副作用的东西。
用法:
Dim result = If(condition, valueWhenTrue, valueWhenFalse)
Dim value = If(obj, valueWhenObjNull)
答案 56 :(得分:1)
ByVal 与 ByRef 关键字之间的差异:
Module Module1
Sub Main()
Dim str1 = "initial"
Dim str2 = "initial"
DoByVal(str1)
DoByRef(str2)
Console.WriteLine(str1)
Console.WriteLine(str2)
End Sub
Sub DoByVal(ByVal str As String)
str = "value 1"
End Sub
Sub DoByRef(ByRef str As String)
str = "value 2"
End Sub
End Module
'Results:
'initial
'value 2
答案 57 :(得分:1)
有一天,基本用户没有引入任何变量。他们只是通过使用它们来介绍它们。引入VB的Option Explicit只是为了确保你不会因输入错误而错误地引入任何变量。您可以随时将其关闭,体验我们使用Basic的日子。
答案 58 :(得分:1)
我曾经非常喜欢可选的函数参数,但我现在使用它们的次数较少,因为我必须经常在C#和VB之间来回走动。 C#何时会支持他们? C ++甚至C都有它们(一种)!
答案 59 :(得分:1)
代码文档
''' <summary>
'''
''' </summary>
''' <remarks></remarks>
Sub use_3Apostrophe()
End Sub
答案 60 :(得分:0)
Sub Main()
Select Case "value to check"
'Check for multiple items at once:'
Case "a", "b", "asdf"
Console.WriteLine("Nope...")
Case "value to check"
Console.WriteLine("Oh yeah! thass what im talkin about!")
Case Else
Console.WriteLine("Nah :'(")
End Select
Dim jonny = False
Dim charlie = True
Dim values = New String() {"asdff", "asdfasdf"}
Select Case "asdfasdf"
'You can perform boolean checks that has nothing to do with your var.,
'not that I would recommend that, but it exists.'
Case values.Contains("ddddddddddddddddddddddd")
Case True
Case "No sense"
Case Else
End Select
Dim x = 56
Select Case x
Case Is > 56
Case Is <= 5
Case Is <> 45
Case Else
End Select
End Sub
答案 61 :(得分:0)
方法的属性!例如,在设计时不应该可用的属性可以是1)对属性窗口隐藏,2)未序列化(特别是对于用户控件或从数据库加载的控件很烦):
<System.ComponentModel.Browsable(False), _
System.ComponentModel.DesignerSerializationVisibility(System.ComponentModel.DesignerSerializationVisibility.Hidden), _
System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Always), _
System.ComponentModel.Category("Data")> _
Public Property AUX_ID() As String
<System.Diagnostics.DebuggerStepThrough()> _
Get
Return mAUX_ID
End Get
<System.Diagnostics.DebuggerStepThrough()> _
Set(ByVal value As String)
mAUX_ID = value
End Set
End Property
如果您进行任何调试,请加入DebuggerStepThrough()
非常有帮助(请注意,您仍然可以在函数或其他内容中设置断点,但您可以单步执行该功能。
此外,将事物分类(例如“数据”)的能力意味着,如果您做希望该属性显示在属性工具窗口中,那么该特定属性将显示在那个类别中。
答案 62 :(得分:0)
再次选择参数!
Function DoSmtg(Optional a As string, b As Integer, c As String)
'DoSmtg
End
' Call
DoSmtg(,,"c argument")
DoSmtg(,"b argument")
答案 63 :(得分:-3)
我的关键字
“我”关键字在VB.Net中是唯一的。我知道它很常见,但“我”与C#等效“this”之间存在差异。不同之处在于“这个”是只读的而“我”不是。这在构造函数中是有价值的,在这种构造函数中,你有一个变量实例,你想要构造的变量已经相等,因为你可以设置“Me = TheVariable”而不是C#,你必须手动复制变量的每个字段(如果有很多字段并且容易出错,那就太可怕了。 C#的解决方法是在构造函数之外进行赋值。这意味着你现在如果对象是自我构建到一个完整的对象,你现在需要另一个函数。