[英]Convert VB.NET delegate to C#
I would like to convert this single line of code from VB.NET to C#:我想将这行代码从 VB.NET 转换为 C#:
Private callback As clsCompareLibs.ResultCallback = AddressOf zipCallback
How can I convert the above code to C#?如何将上述代码转换为 C#? The application works if I add the following lines of code, but without the progressbar and the function zipCallback is called, but never enters the else part:如果我添加以下代码行,应用程序就可以工作,但没有进度条,并且调用了 zipCallback 函数,但从不进入 else 部分:
public delegate void zipCallbackHendler(ref CompareLibs.ZipData _zipData);
zipCallbackHendler ziphandler;
CompareLibs.ResultCallback callback/*=ziphandler*/;
The code for zipCallback: zipCallback 的代码:
Private Sub zipCallback(ByRef zipData As clsCompareLibs.ZipData)
Static lastName As String
If Me.InvokeRequired Then
Me.Invoke(callback, zipData)
Else
With zipData
If .fileList IsNot Nothing AndAlso .fileList.Count > 0 Then
' We've received a list of files. Add them to the listbox.
Dim names As New List(Of String)
currentEntries.Clear()
For Each entry As clsCompareLibs.ShortEntry In .fileList
names.Add(entry.name)
currentEntries.Add(entry)
Next
Me.lbFileList.Items.AddRange(names.ToArray())
Me.lblFileName.Text = "Complete."
Try
zipLib.Close()
Catch ex As Exception
End Try
me.Cursor = System.Windows.Forms.Cursors.Default
Else
' We're updating the UI with progress data here.
' Have we moved on to a new file?
If lastName <> zipData.currentFileName Then
' If so, set the progress bar to 0.
pbCurrentFile.Value = 0
lastName = zipData.currentFileName
End If
lblFileName.Text = .operationTitle
If .currentFileName <> "" Then lblFileName.Text += ": ...\" & Path.GetFileName(.currentFileName)
If .currentFileBytesCopied > 0 AndAlso .totalBytes > 0 Then
pbCurrentFile.Value = CInt((.currentFileBytesCopied / .currentFileLength) * 100)
pbTotalBytes.Value = CInt((.totalBytesCopied / .totalBytes) * 100)
pbCurrentFile.Refresh()
pbTotalBytes.Refresh()
End If
If .complete Then
zipLib.Close()
If .cancel Then
lblFileName.Text = "Canceled."
pbCurrentFile.Value = 0
pbTotalBytes.Value = 0
Else
endTime = Now
If endTime.Subtract(startTime).TotalSeconds > 60 then
lblFileName.Text = "Complete. This operation took " & _
endTime.Subtract(startTime).Minutes.ToString() & _
" minutes, and " & endTime.Subtract(startTime).Seconds.ToString() & " seconds."
Else
lblFileName.Text = "Complete. This operation took " & _
endTime.Subtract(startTime).TotalSeconds.ToString("N1") & _
" seconds."
End If
End If
tsbZipFiles.Visible = True
tsbZipFiles.Enabled = True
tsbListZipEntries.Visible = True
tsbCancel.Visible = False
me.Cursor = System.Windows.Forms.Cursors.Default
End If
If .errorMessage <> "" Then
MsgBox("" & .errorMessage, MsgBoxStyle.Critical, "Zip Example App")
me.Cursor = System.Windows.Forms.Cursors.Default
End If
End If
End With
End If
End Sub
In main:在主要:
zipLib = New clsCompareLibs(zipPath, clsCompareLibs.ZipAccessFlags.Create, 1024 * 1024, _
cbDotNetZip.Checked, CInt(nudCompression.Value), cbZip64.Checked, tbPassword.Text, 100, AddressOf zipCallback)
ResultCallback:结果回调:
Public Delegate Sub ResultCallback(ByRef _zipData As ZipData)
The zipCallback
method is a member of a class. zipCallback
方法是一个类的成员。 Since the method might use other members of that class type, you also need an instance of the class to use with the delegate, so the code knows what instance to look at if another member is referenced.由于该方法可能使用该类类型的其他成员,因此您还需要该类的一个实例与委托一起使用,因此代码知道如果引用另一个成员时要查看哪个实例。
To help understand, think about this code:为了帮助理解,请考虑以下代码:
Public Class Foo
Public A As String
Public Sub Bar(Baz As String)
A = A & Baz
End Sub
End Class
Dim x As New Foo With {.A = "x"}
Dim y As New Foo With {.A = "y"}
Now imagine trying to use Foo.Bar()
as your delegate callback.现在想象一下尝试使用Foo.Bar()
作为您的委托回调。 You'd see different results depending on whether you use the x
instance or the y
instance.根据您使用的是x
实例还是y
实例,您会看到不同的结果。 Which one do we want?我们要哪一个? Or maybe we meant a different instance completely.或者也许我们的意思是完全不同的实例。 The point is you need to know.关键是你需要知道。
Instead of this:取而代之的是:
AddressOf Bar
you need this:你需要这个:
AddressOf x.Bar
or或者
AddressOf y.Bar
The original project manages this with an implied Me
instance reference ( this
in C#). 原始项目使用隐含的Me
实例引用(在 C# 中为this
)来管理它。 It works because the zipCallback()
and the code using it with AddressOf
are both in the same class , and so we have an implied instance.它有效是因为zipCallback()
和使用它的代码与AddressOf
都在同一个 class 中,所以我们有一个隐含的实例。
It's not clear this remains true with the code in the question.目前尚不清楚问题中的代码是否仍然如此。 If the zipCallback()
method has moved to a different class from the Main
class in the project, you'll need to know which instance of the class you're using as part of the AddressOf
statement.如果zipCallback()
方法已从项目中的Main
类移至不同的类,则您需要知道您正在使用该类的哪个实例作为AddressOf
语句的一部分。
For completeness, the other option is VB code using a Module
instead of a Class
.为了完整起见,另一个选项是使用Module
而不是Class
VB代码。 In that case, the equivalent C# should have a static class
and the method should also be marked static
( Shared
in VB parlance).在这种情况下,等效的 C# 应该有一个static class
并且该方法也应该标记为static
(在 VB 中为Shared
)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.