진행 바로 비동기에 FsXaml 응용 프로그램

0

질문

F# (FsXaml/뒤에 코드) 응용 프로그램을 사용하고 싶 진행 표시줄 없이 이용의 배경을 작업자로서 내가 할 수 있습니다. 기반으로 기사를 인터넷에서(연결은 여기에서),나를 사용하여 비동기 워크플로우를 경험할 수 있습니다.

내가 만들어 코드 기반의(일부 확장)에 예에서 앞서 언급한 문서지만,그것은 작동하지 않았으로 예상된다. 현재 실 UI(thread)는 여전히 차단되지 않은 경우 비동기 코드가 있었다. 아 전환하면 백그라운드 스레드가 발생합니다. 바로 활성화한 후에만 긴 실행 중인 작업이 완료되었습니다. 을 제거하 onThreadPool 기능을 효과가 없습니다.

나의 질문은 무엇이 잘못된 코드고 어떻게 그것이 옳은가?

type MainWindowXaml = FsXaml.XAML<"XAMLAndCodeBehind/MainWindow.xaml">

type MainWindow() as this =

    inherit MainWindowXaml()

    //....some code....

    let ButtonClick _ = 
   
        //....some code....
       
        let longRunningOperation() = //....some long running operation (reading from Google Sheets)....            
             
        let progressBar() = this.ProgressBar.IsIndeterminate <- true     

        let doBusyAsync progress operation =  
            progress
            async
                {   
                  do! operation
                }
            |> Async.StartImmediate 
    
        let onThreadPool operation =
            async
                {    
                  let context = System.Threading.SynchronizationContext.Current
                  do! Async.SwitchToThreadPool()
                  let! result = operation
                  do! Async.SwitchToContext context
                  return result
                } 
    
        let asyncOperation progress operation =   
            async { operation } 
            |> onThreadPool
            |> doBusyAsync progress 
    
        (progressBar(), longRunningOperation()) ||> asyncOperation 
      
    do
        //....some code....
        this.Button.Click.Add ButtonClick
asynchronous f# fsxaml
2021-11-23 23:13:28
2

최고의 응답

3

의 수가 있는 것으로 잘못 코드입니다.

  • 첫째, progressBar(), longRunningOperation() 당신이 실제로 부르의 오래 실행되는 작업 그래서 모두가 여기에서 실행된다. (로 추측에서 불완전한 샘플 이 함수 호출,다른 비동기 조작).

  • 당신은 다음을 통과하는 결과 operationprogress 의 주위에,그러나 그들은 단지 unit 하지 않는 값은 실제로는 아무것도하지.

  • 따라서,비동기 작업 async { operation } 에 전달하는 onThreadPool 아무것도 하지 않는다.

  • doBusyAsync를 사용하여 Async.StartImmediate 를 실행하는 작업에 차단하는 방법은(그래서 이것을 차단하 실 경우에도,그것을 실행하는 실제 동작).

  • 고객께서는 차단,당신은 또한 당신이 필요하지 않습 async { do! operation } 기 때문에 이에 해당하 operation.

요약하면,당신의 코드를 어떻게든 방법으로도 복잡하다. 당신은 그것을 단순화해야하는 무언가가 매우 기본적으로 첫 번째 단계입니다. 나지 않아 오른쪽 설정이지만,나는 무언가를 생각하는 다음과 같이 할 수 있습니다.:

let ButtonClick _ = 
  let longRunningOperation() = 
    // some long-running operation

  let asyncOperation() = async {
    // Start the progress bar here
    let context = System.Threading.SynchronizationContext.Current
    do! Async.SwitchToThreadPool()
    let result = longRunningOperation()
    do! Async.SwitchToContext context
    // Display the 'result' in your user interface
    // Stop the progress bar here
  }

  Async.Start(asyncOperation)

나는 모두 제거한 다양한 기능 또한 제공합니다.고 매개 변수를 전달하고 단순화 가능한 한 많이-그것은 당신의 장기 실행 작업이라고 하는에서 직접 async 그것은 스위치를 실 수 있습니다. 당신은 당신의 결과로 전환한 후 다시 원래의 컨텍스트할 수 있어야 하는 표시에 사용자 인터페이스가 있습니다. 이상적으로,당신은 확인 longRunningOperation 자체 비동기(호출을 사용하여 let!다)하지만 위의 작업해야 합니다.

2021-11-24 00:15:43
0

일을 요약하면,나는 확장된 공 Petříček 의 코드를 가진 코드에 관련된 오래 실행되는 작업에 기반한 짐 포이의 댓글(에 대한 호핑에 다시 UI thread). 코드는 지금처럼 작동하는 곳입니다. 내 감사하여 공 Petříček 을 위해 자신의 종류와는 상세한 대답합니다.

    let low = string (this.TextBox2.Text)
    let high = string (this.TextBox3.Text)
    let path = string (this.TextBox4.Text)

    (* longRunningOperation() replaced by textBoxString4() and textBoxString3() 
       based on the comment by Jim Foye
    
    let longRunningOperation() = 
        async
            {
              match textBoxString4 low high >= 0 with
              | false -> this.TextBox1.Text <- textBoxString3 low high path 
              | true  -> this.TextBox1.Text <- "Chybný rozdíl krajních hodnot"        
            }
    *)

    let textBoxString4() = 
        async
            {
              let result = textBoxString4 low high
              return result
            }                  
                           
    let textBoxString3() =        
        async
            {
              //the actual long running operation (reading data 
              //from Google Sheets)
              let result = textBoxString3 low high path 
              return result
            }  

    let asyncOperation() = 
        async
            {
              let context = System.Threading.SynchronizationContext.Current
              this.ProgressBar2.IsIndeterminate <- true
              do! Async.SwitchToThreadPool()
              (*let! result = longRunningOperation() throws an exception 
              "The calling thread cannot access this object because
               a different thread owns it." 
              *)
              let! result4 = textBoxString4()  
              let! result3 = textBoxString3()  
              do! Async.SwitchToContext context
              match result4 >= 0 with
              | false -> this.TextBox1.Text <- result3
              | true  -> this.TextBox1.Text <- "Chybný rozdíl krajních hodnot" 
              this.ProgressBar2.IsIndeterminate <- false
            } 
    Async.StartImmediate(asyncOperation())//not working with Async.Start
                                             
2021-11-24 18:29:36

다른 언어로

이 페이지는 다른 언어로되어 있습니다

Русский
..................................................................................................................
Italiano
..................................................................................................................
Polski
..................................................................................................................
Română
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................