2013-02-26 5 views
1

MCSD 시험의 일부인 비동기 호출에 대해 자세히 배우려고합니다. 다음 페이지의 모든 예제를 성공적으로 따라갔습니다 : http://msdn.microsoft.com/en-gb/library/2e08f6yc.aspx.비동기 호출이 완료 될 때 콜백 메서드 실행

모든 예제의 콘솔 응용 프로그램과 Winform 응용 프로그램을 만들었습니다. 그러나 콜백 함수는 WinForm 응용 프로그램이 사용되는 경우 마지막 예제 (비동기 호출이 완료되면 콜백 메서드 실행)에서 호출되지 않습니다. 아래 코드를 참조하십시오 :

Imports System 
Imports System.Threading 
Imports System.Runtime.InteropServices 

Public Class AsyncDemo 
    ' The method to be executed asynchronously. 
    ' 
    Public Function TestMethod(ByVal callDuration As Integer, _ 
      <Out()> ByRef threadId As Integer) As String 
     Console.WriteLine("Test method begins.") 
     Thread.Sleep(callDuration) 
     threadId = AppDomain.GetCurrentThreadId() 
     Return "MyCallTime was " + callDuration.ToString() 
    End Function 
End Class 

' The delegate must have the same signature as the method 
' you want to call asynchronously. 
Public Delegate Function AsyncDelegate(ByVal callDuration As Integer, _ 
    <Out()> ByRef threadId As Integer) As String 

Public Class AsyncMain 
    ' The asynchronous method puts the thread id here. 
    Private Shared threadId As Integer 

    Shared Sub Main() 
     ' Create an instance of the test class. 
     Dim ad As New AsyncDemo() 

     ' Create the delegate. 
     Dim dlgt As New AsyncDelegate(AddressOf ad.TestMethod) 

     ' Initiate the asynchronous call. 
     Dim ar As IAsyncResult = dlgt.BeginInvoke(3000, _ 
      threadId, _ 
      AddressOf CallbackMethod, _ 
      dlgt) 

     Console.WriteLine("Press Enter to close application.") 
     Console.ReadLine() 
    End Sub 

    ' Callback method must have the same signature as the 
    ' AsyncCallback delegate. 
    Shared Sub CallbackMethod(ByVal ar As IAsyncResult) 
     ' Retrieve the delegate. 
     Dim dlgt As AsyncDelegate = CType(ar.AsyncState, AsyncDelegate) 

     ' Call EndInvoke to retrieve the results. 
     Dim ret As String = dlgt.EndInvoke(threadId, ar) 

     Console.WriteLine("The call executed on thread {0}, with return value ""{1}"".", threadId, ret) 
    End Sub 
End Class 

왜 WinForm 응용 프로그램에서 CallbackMethod에 도달하지 않았습니까? 콘솔 응용 프로그램과 WinForm 응용 프로그램의 차이점을 이해합니다.

+0

WinForms 프로젝트가'Main()'메소드에서 시작하도록 설정 했습니까? 비동기 함수 자체가 호출 되었습니까? –

+0

@Nico Schertler, 네. 나는 '응용 프로그램 프레임 워크 사용'을 해제하고 기본 방법에 도달했습니다. – w0051977

답변

2

문제는 Console.ReadLine()입니다. WinForms 앱에서는이 호출이 차단되지 않습니다. 대신 Thread.Sleep(Timeout.Infinite) 또는 귀하의 필요에 가장 적합한 것을 사용할 수 있습니다.

+0

블록 단위의 의미를 설명해 주시겠습니까? 비동기 처리에 비교적 익숙하지 않습니다. – w0051977

+0

그래도 효과가 있습니다. +1. – w0051977

+0

콘솔 앱에서 'ReadLine()'은 사용자가 돌아 오기 전까지는 반환하지 않습니다. 그래서'Main()'은 그 때까지 남아 있지 않습니다. 이것은 WinForms의 경우는 아닙니다. 따라서 비동기 호출이 반환되기 전에'Main()'이 남아 있습니다. 비동기 호출이 백그라운드 스레드이기 때문에 더 이상의 포 그라운드 스레드가 없으므로 응용 프로그램이 종료됩니다. –

관련 문제