Có VB.NET tương đương với C # 's' ?? ' nhà điều hành?


180

Có VB.NET tương đương với ??toán tử của C # không?


4
Hầu hết các câu trả lời ở đây (bao gồm cả câu trả lời được chấp nhận) đều không đúng và không có chức năng tương đương với ?? trong mọi tình huống. Tương đương đúng là câu lệnh if () có 2 đối số. Tuy nhiên, đối số thứ hai có thể được lồng nhau để đạt được kết quả chính xác như ?? với nhiều đối số.
dùng1751825

Ý bạn là toán tử ternary ?: Vd return ((value <0)? True: false)
Zeek2

Câu trả lời:


155

Sử dụng If()toán tử với hai đối số ( tài liệu Microsoft ):

' Variable first is a nullable type.
Dim first? As Integer = 3
Dim second As Integer = 6

' Variable first <> Nothing, so its value, 3, is returned.
Console.WriteLine(If(first, second))

second = Nothing
' Variable first <> Nothing, so the value of first is returned again. 
Console.WriteLine(If(first, second))

first = Nothing second = 6
' Variable first = Nothing, so 6 is returned.
Console.WriteLine(If(first, second))

3
Tôi nghĩ rằng If()tuyên bố trong VB giống như if...?...:trong C #, không phải là ??toán tử
Luke T O'Brien

2
@ LukeTO'Brien Đó là nếu bạn sử dụng nó với 3 đối số. Nếu bạn sử dụng nó với 2 đối số, thì nhiều hơn thế ??(xem câu trả lời khác cho câu hỏi này: stackoverflow.com/a/20686360/1474939 )
Brian J

2
Câu trả lời này cho thấy cách sử dụng VB If với ba tham số . Điều đó không giống với ??toán tử của C # . Câu trả lời tốt hơn là Code Maverick's If với hai đối số . (Nick đã có câu trả lời tương tự, nhiều năm trước, nhưng không bao gồm lời giải thích từ MSDN.)
ToolmakerSteve

1
Điều này trả lời một câu hỏi hoàn toàn khác nhau.
Marc Gravell

1
Để hiểu các ý kiến ​​trước đó, hãy nhìn vào lịch sử chỉnh sửa.
Zev Spitz


70

Câu trả lời được chấp nhận không có bất kỳ lời giải thích nào và chỉ đơn giản là một liên kết.
Do đó, tôi nghĩ rằng tôi sẽ để lại câu trả lời giải thích cách thức Ifhoạt động của toán tử được lấy từ MSDN:


Nếu toán tử (Visual Basic)

Sử dụng đánh giá ngắn mạch để trả về có điều kiện một trong hai giá trị. Các Nếu nhà điều hành có thể được gọi với ba đối số hoặc với hai đối số.

If( [argument1,] argument2, argument3 )


Nếu toán tử gọi với hai đối số

Đối số đầu tiên thành If có thể được bỏ qua. Điều này cho phép toán tử được gọi bằng cách chỉ sử dụng hai đối số. Danh sách sau chỉ áp dụng khi toán tử If được gọi với hai đối số.


Các bộ phận

Term         Definition
----         ----------

argument2    Required. Object. Must be a reference or nullable type. 
             Evaluated and returned when it evaluates to anything 
             other than Nothing.

argument3    Required. Object.
             Evaluated and returned if argument2 evaluates to Nothing.


Khi đối số Boolean bị bỏ qua, đối số đầu tiên phải là kiểu tham chiếu hoặc nullable. Nếu đối số thứ nhất ước lượng thành Không có gì , giá trị của đối số thứ hai được trả về. Trong tất cả các trường hợp khác, giá trị của đối số đầu tiên được trả về. Ví dụ sau minh họa cách đánh giá này hoạt động.


VB

' Variable first is a nullable type. 
Dim first? As Integer = 3
Dim second As Integer = 6

' Variable first <> Nothing, so its value, 3, is returned.
Console.WriteLine(If(first, second))

second = Nothing 
' Variable first <> Nothing, so the value of first is returned again.
Console.WriteLine(If(first, second))

first = Nothing
second = 6
' Variable first = Nothing, so 6 is returned.
Console.WriteLine(If(first, second))

Một ví dụ về cách xử lý nhiều hơn hai giá trị (lồng nhau if):

Dim first? As Integer = Nothing
Dim second? As Integer = Nothing
Dim third? As Integer = 6
' The LAST parameter doesn't have to be nullable.
'Alternative: Dim third As Integer = 6

' Writes "6", because the first two values are "Nothing".
Console.WriteLine(If(first, If(second, third)))

18

Bạn có thể sử dụng một phương pháp mở rộng. Cái này hoạt động giống như SQL COALESCEvà có thể là quá mức cần thiết cho những gì bạn đang cố kiểm tra, nhưng nó hoạt động.

    ''' <summary>
    ''' Returns the first non-null T based on a collection of the root object and the args.
    ''' </summary>
    ''' <param name="obj"></param>
    ''' <param name="args"></param>
    ''' <returns></returns>
    ''' <remarks>Usage
    ''' Dim val as String = "MyVal"
    ''' Dim result as String = val.Coalesce(String.Empty)
    ''' *** returns "MyVal"
    '''
    ''' val = Nothing
    ''' result = val.Coalesce(String.Empty, "MyVal", "YourVal")
    ''' *** returns String.Empty
    '''
    ''' </remarks>
    <System.Runtime.CompilerServices.Extension()> _
    Public Function Coalesce(Of T)(ByVal obj As T, ByVal ParamArray args() As T) As T

        If obj IsNot Nothing Then
            Return obj
        End If

        Dim arg As T
        For Each arg In args
            If arg IsNot Nothing Then
                Return arg
            End If
        Next

        Return Nothing

    End Function

Tích hợp If(nullable, secondChoice)chỉ có thể xử lý hai lựa chọn nullable. Ở đây, người ta có thể có Coalescenhiều tham số như mong muốn. Cái không null đầu tiên sẽ được trả về và phần còn lại của các tham số không được đánh giá sau đó (ngắn gọn, như AndAlso/ &&OrElse/ ||)


8
Bởi vì ngôn ngữ có một toán tử tích hợp. Không có lý do để thậm chí nhìn vào các phương pháp mở rộng.
Nick

2
Tôi sẽ không lặp lại câu trả lời của người khác. Tôi hình dung rằng có thể tốt để cung cấp một giải pháp thay thế nếu bạn cần kiểm tra nhiều giá trị bằng một câu lệnh. Vì nó không phải là một câu trả lời SAU, vậy nó có nên bị hạ cấp không?
Cá đuối gai độc

1
+1 để cung cấp triển khai bằng cách sử dụng thuốc generic và tránh loại / quyền anh / unboxing
ulty4life

4
@Nick, xin lỗi, nhưng bạn hoàn toàn sai. Nếu bạn có nhiều hơn hai đối số kết hợp, hàm tích hợp sẽ không cắt nó.
chập chững

Bạn có thể bỏ qua obj param và để cho cơ thể là Return args.FirstOrDefault(Function(arg) arg IsNot Nothing):-)
Ulf kerstedt

11

Một hạn chế đáng kể của hầu hết các giải pháp này là chúng sẽ không bị đoản mạch. Do đó chúng không thực sự tương đương với ??.

Việc xây dựng trong Ifđiều hành sẽ không đánh giá các thông số tiếp theo trừ khi đánh giá lại số trước đó để không có gì.

Các câu sau đây là tương đương:

C #

var value = expression1 ?? expression2 ?? expression3 ?? expression4;

VB

dim value = if(expression1,if(expression2,if(expression3,expression4)))

Điều này sẽ làm việc trong tất cả các trường hợp ??làm việc. Bất kỳ giải pháp nào khác sẽ phải được sử dụng hết sức thận trọng, vì chúng có thể dễ dàng đưa ra các lỗi thời gian chạy.


Điều này không hoạt động trong trường hợp có một số lượng tham số không xác định (tốt .. không phải không sử dụng roslyn hoặc codedom để biên dịch trước một câu lệnh để khớp với số lượng tham số tại thời điểm đó trong khi thực thi).
StingyJack

@StingyJack Nó không có ý định. Nó làm chính xác những gì ?? Toán tử nào.
dùng1751825

2

Kiểm tra tài liệu của Microsoft về If Toán tử (Visual Basic) tại đây: https://docs.microsoft.com/en-us/dotnet/visual-basic/lingu-reference/operators/if-operator

If( [argument1,] argument2, argument3 )

Dưới đây là một số ví dụ (VB.Net)

' This statement prints TruePart, because the first argument is true.
Console.WriteLine(If(True, "TruePart", "FalsePart"))

' This statement prints FalsePart, because the first argument is false.
Console.WriteLine(If(False, "TruePart", "FalsePart"))

Dim number = 3
' With number set to 3, this statement prints Positive.
Console.WriteLine(If(number >= 0, "Positive", "Negative"))

number = -1
' With number set to -1, this statement prints Negative.
Console.WriteLine(If(number >= 0, "Positive", "Negative"))

1
Đẹp! Xóa bình luận!
Alec
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.