0

I apologize if this is documented somewhere, I could not find the answer using an underscore in this specific manner (an If Not, AndAlso statement).

Here is what I don't understand

If Not variable Is Nothing _
    AndAlso Not Results.Tables.Count = 0 _
    AndAlso Not Results.Tables(0).Rows.Count = 0 Then

If I take away the Underscores in this code, VB2017 automatically puts a Then at the end of the first line of code and I get 2 Syntax Errors for AndAlso on both lines they are used. Can someone explain why this is? I read on StackOverflow that the Compiler doesn't care about the underscore, and I've also read MSDN's AndAlso documentation and I'm a little confused.

Thank you for your help.

CodingWrong
  • 17
  • 1
  • 2
  • 3
    `_` is the **line-continuation** character that allows you to to write code that spans multiple lines. VB does not allow line-breaks inside expressions or statements by default. – Dai Aug 31 '18 at 19:39
  • Thank you for your response, that doesn't seem to be the case here, if I make it all one line of code I still get a Syntax Error, but only on the First AndAlso. – CodingWrong Aug 31 '18 at 19:42
  • 3
    `I apologize if this is documented somewhere` - https://learn.microsoft.com/en-us/dotnet/visual-basic/programming-guide/program-structure/how-to-break-and-combine-statements-in-code. Implicit line continuation [first appeared in VB 2010](https://learn.microsoft.com/en-us/dotnet/visual-basic/getting-started/whats-new). – GSerg Aug 31 '18 at 19:43
  • I'm an idiot, thank you. My IDE was adding Then's in, regardless of making it one line causing Syntax Errors. – CodingWrong Aug 31 '18 at 19:47

4 Answers4

9

I read on StackOverflow that the Compiler doesn't care about the underscore

That's not quite true. Implicit line continuations are a fairly recent addition to the Visual Basic language1. They cover many, but not all, scenarios where the _ line continuation character used to be needed.

Here's the complete list from linked documentation:

  • After a comma (,).
  • After an open parenthesis (() or before a closing parenthesis ()).
  • After an open curly brace ({) or before a closing curly brace (}).
  • After an open embedded expression (<%=) or before the close of an embedded expression (%>) within an XML literal.
  • After the concatenation operator (&). For example:
  • After assignment operators (=, &=, :=, +=, -=, *=, /=, \=, ^=, <<=, >>=).
  • After binary operators (+, -, /, *, Mod, <>, <, >, <=, >=, ^, >>, <<, And, AndAlso2, Or, OrElse, Like, Xor) within an expression.
  • After the Is and IsNot operators.
  • After a member qualifier character (.) and before the member name.

This shows we can safely add lines after AndAlso rather than before:

If Not variable Is Nothing AndAlso
   Not Results.Tables.Count = 0 AndAlso 
   Not Results.Tables(0).Rows.Count = 0 Then

I also suggest rewriting as follows, because VB.Net does odd things with Not, using it as a bitwise rather than logical operator3:

If variable IsNot Nothing AndAlso
   Results.Tables.Count > 0 AndAlso 
   Results.Tables(0).Rows.Count > 0 Then

1. Okay, 2010, but I still find a lot of VB developers who don't know about them, or know about them but never check the rules and either avoid them or let the compiler tell them when to add one.
2. Emphasis mine.
3. Plus, I just find it easier to read without the negations.

Joel Coehoorn
  • 399,467
  • 113
  • 570
  • 794
  • This makes sense, I was wondering why I hadn't remembered dealing with underscores recently, but was seeing OP's behavior on my side when I copied into the IDE. – Parrish Husband Aug 31 '18 at 20:12
1

"if I make it all one line of code I still get a Syntax Error"

This compiles fine:

If Not variable Is Nothing AndAlso Not Results.Tables.Count = 0 AndAlso Not Results.Tables(0).Rows.Count = 0 Then Exit Sub

This also compiles fine:

If Not variable Is Nothing _
        AndAlso Not Results.Tables.Count = 0 _
        AndAlso Not Results.Tables(0).Rows.Count = 0 Then Exit Sub

What won't work is this:

If Not variable Is Nothing
        AndAlso Not Results.Tables.Count = 0 
        AndAlso Not Results.Tables(0).Rows.Count = 0 Then Exit Sub

Without the _ underscore it expects the If statement to be fully formed on the same line.

As Joel points out, the implicit line continuations require the AndAlso before the line break. See his better answer.

What's good to know however is that the underscores are not necessary when using Linq in newer versions of the compiler:

Dim interesting = From r As DataRow In Results.Tables(0).AsEnumerable()
                  Let fieldId = r.Field(Of Integer)("id")
                  Where fieldId <> 0
                  Order By fieldId
                  Select r
Parrish Husband
  • 3,148
  • 18
  • 40
  • Thank you for the clear explanation. When I made it all one line my IDE jumped the gun and added more Then Statements causing the Syntax error. Thanks for the effort and break down. I appreciate it. – CodingWrong Aug 31 '18 at 19:52
  • Ahh I see now the IDE was borking it for you. Look into `variable IsNot Nothing` I find it ends up being more concise to read. – Parrish Husband Aug 31 '18 at 19:53
0

It means "line continues on next line".

You can also write it as:

If variable IsNoT Nothing AndAlso 
   Results.Tables.Count > 0 AndAlso 
   Results.Tables(0).Rows.Count > 0 Then
       'something
End If
CruleD
  • 1,153
  • 2
  • 7
  • 15
0

The conditions in the If statement must be on one line as a VB standard. because some conditions might be too long to be readable on one line, the underscore is used as an escape character that indicates that the line is not finished. If you write

 If Not variable Is Nothing 
AndAlso Not Results.Tables.Count = 0 
AndAlso Not Results.Tables(0).Rows.Count = 0 Then

Visual stdio will only consider the first line as part of the If statement Making the result:

 If Not variable Is Nothing Then
 AndAlso Not Results.Tables.Count = 0 
 AndAlso Not Results.Tables(0).Rows.Count = 0 Then

You will need to put all conditions on one line or use the underscore. This is the standard in VB.