Reputation: 5534
I have this code i'm trying to convert from C# to VB.net:
public object Invoke(object instance, object[] inputs, out object[] outputs)
{
// Create a new, STA thread
object[] staOutputs = null;
object retval = null;
Thread thread = new Thread(
delegate(){
retval = _innerInvoker.Invoke(instance, inputs, out staOutputs);
});
thread.SetApartmentState(ApartmentState.STA);
thread.Start();
thread.Join();
outputs = staOutputs;
return retval;
}
The whole delegate thing is throwing me off. Can anyone help me convert this? Or is there an article that explains how to do it?
Upvotes: 2
Views: 3359
Reputation: 8007
My fav way to do this is to compile in C#, and then use reflector to see what it looks like in other dotNET languages.
Friend Class Program
' Methods '
Private Shared Function Foo(ByVal instance As Object, ByVal inputs As Object(), <Out> ByRef outputs As Object()) As Object
outputs = Nothing
Return Nothing
End Function
Public Function Invoke(ByVal instance As Object, ByVal inputs As Object(), <Out> ByRef outputs As Object()) As Object
Dim staOutputs As Object() = Nothing
Dim retval As Object = Nothing
Dim thread As New Thread(Function
retval = Me._innerInvoker.Invoke(instance, inputs, staOutputs)
End Function)
thread.SetApartmentState(ApartmentState.STA)
thread.Start
thread.Join
outputs = staOutputs
Return retval
End Function
' Fields '
Private _innerInvoker As MyInvoker = New MyInvoker(AddressOf Program.Foo)
End Class
<CompilerGenerated> _
Private NotInheritable Class <>c__DisplayClass1
' Methods '
Public Sub <Invoke>b__0()
Me.retval = Me.<>4__this._innerInvoker.Invoke(Me.instance, Me.inputs, Me.staOutputs)
End Sub
' Fields '
Public <>4__this As Program
Public inputs As Object()
Public instance As Object
Public retval As Object
Public staOutputs As Object()
End Class
Upvotes: 6
Reputation: 21742
SOmethiong like the following ought to it: (Where _ are private fields (this is not production rdy but hope fully give you the idea)
Public Function Invoke(instance As Object, inputs As Object(), ByRef outputs As Object()) As Object
' Create a new, STA thread
Dim staOutputs As Object() = Nothing
Dim retval As Object = Nothing
Dim thread As New Thread(AddressOf(Do))
_instance = instance
_inputs = inputs
_staOutPuts = staOutputs
thread.SetApartmentState(ApartmentState.STA)
thread.Start()
thread.Join()
outputs = staOutputs
Return retval
End Function
private Function Do() as Object
Return _innerInvoker.Invoke(_instance, _inputs, _staOutputs)
end Function
Upvotes: 1
Reputation: 415735
It's an anonymous function, and VB.Net does not support anonymous functions like that (assuming .Net 2.0, since in .Net 3.5 that would be written as a lambda expression).
The best you can do in VB.Net is add the anonymous function (the delegate) as a separate method in the same class and use the AddressOf operator to reference this new method.
Update:
Reading your code again, the translation is complicated because your anonymous method will be interpreted as a closure, and that means the C# compiler does a complicated transformation on the code before turning it into IL; a whole new class is created is to capture (close over) the local variables referred to in the method:
Class InnerInvokerClosure
Public instance As Object
Public inputs() As Object
Public staOutputs() As Object
Public retValue As Object
Public _innerInvoker As SomeDelegateType
Sub New(ByRef instance as Object, ByRef inputs() as Object, ByRef staOutputs() As Object, ByRef retValue As Object, ByRef _innerInvoker As SomeDelegateType)
Me.instance = instance
Me.inputs = inputs
Me.staOoutputs = staOutputs
Me.retValue = retValue
Me._innerInvoker = _innerInvoker
End Sub
Public Function Invoke() As Object
retValue = _innerInvoker.Invoke(instance, inputs, staOutputs);
End Function
End Class
Public Function Invoke(ByVal instance As Object, ByVal inputs() as Object, ByRef outputs() As Object) As Object
Dim closure As New InnerInvokerClosure(instance, inputs, Nothing, Nothing, _innerInvoker)
Dim t As New Thread(AddressOf closure.Invoke)
t.SetApartmentState(ApartmentState.STA)
t.Start()
t.Join()
outputs = closure.staOutputs
return closure.retValue
End Function
Note that this translation is untested and probably wrong: the exact transformation can be very complicated.
Upvotes: 8
Reputation: 5534
Here is the final code i used:
Public Function Invoke(ByVal instance As Object, ByVal inputs As Object(), ByRef outputs As Object()) As Object Implements System.ServiceModel.Dispatcher.IOperationInvoker.Invoke
Dim staOutputs As Object() = Nothing
Dim retval As Object = Nothing
Dim thread As New Thread(AddressOf DoWork)
_instance = instance
_inputs = inputs
_staOutPuts = staOutputs
thread.SetApartmentState(ApartmentState.STA)
thread.Start()
thread.Join()
outputs = staOutputs
Return retval
End Function
Private Function DoWork() As Object
Return _innerInvoker.Invoke(_instance, _inputs, _staOutPuts)
End Function
@Rune FS - so close, just needed a little help. Thanks!
Upvotes: 1
Reputation: 29216
there is an online C# to VB converter (and vice-versa) located at http://converter.telerik.com/
I pasted your code in there....I dont know if this is valid VB or if it will work or not, but you can give it a shot.
Public Function Invoke(instance As Object, inputs As Object(), ByRef outputs As Object()) As Object
' Create a new, STA thread
Dim staOutputs As Object() = Nothing
Dim retval As Object = Nothing
Dim thread As New Thread(Function() Do
retval = _innerInvoker.Invoke(instance, inputs, staOutputs)
End Function)
thread.SetApartmentState(ApartmentState.STA)
thread.Start()
thread.Join()
outputs = staOutputs
Return retval
End Function
Upvotes: 0