0

これは私の要件です:

ボタンをクリックすると、データベースからデータを取得し、関数を使用しているdatagridviewに入力する必要があります。取得に時間がかかる場合があり、その間UIを使用したいので、この関数を別のスレッドで実行したいと思います。このために、私は非同期コールバックを使用しています。しかし、begininvoke()endinvoke()関数の間。私はコードを書いていません(UIを応答させるために何を書くべきかわかりません)。

datagridviewは正しく入力されていますが、関数がデータを取得しているときにUIにアクセスしようとすると、UIがブロックされます。

4

3 に答える 3

1

UI スレッドから実行時間の長い操作を開始しないことをお勧めします。最初に別のスレッドを開始してから、その別のスレッドで長時間実行される操作を実行します。完了したら、Form.Invoke() メソッドを使用して結果を UI に戻します。この方法では、UI スレッドは直接影響を受けません。

別のスレッドを手動で作成する代わりに、BackgroundWorkerのような構成を使用することもできます。

UI スレッドから実行時間の長い操作を開始する場合は、 Application.DoEvents() を定期的に呼び出す必要があります (ループ内など)。ただし、長時間実行される操作が IO 集中型の場合 (ほとんどの場合 IO 操作を待機している場合)、 Application.DoEvents() を必要な頻度で呼び出すことはできません。これにより、UI の反応が鈍くなったりぎくしゃくしたりするようになります。上で述べたように、別のスレッドは、この点でより良い方法です。

于 2012-05-17T05:47:36.967 に答える
0

を使用して を作成している場合は、内でメソッドを使用して、 の作成中に UI をレスポンシブのままにするloopことができます。DataGridViewApplication.DoEvents()loopDataGridView

アップデート

BackgroundWorker問題はループではないと述べたように、クラスを使用するのが最善の方法だと思います。

DataGridViewの場合にデータを入力できるDoWork()場所BackgroundWorker

また、コードのBackgroundWorker.DoWork()イベント中にイベントを開始できます。button_click

于 2012-05-17T05:47:19.193 に答える
0

まず、私の場合は DataMgr である中間レベルではなく、UI フォーム自体に asynccallback 関数を作成する必要があります。また、null 値を渡した場所に適切な値を指定して、begininvoke 関数の最後の 2 つのパラメーターを追加する必要があります。そのはず

MethodDelegate dlgt = new MethodDelegate(DataMgr.countIssuingEntities);
 TempValueHolder tmp = new TempValueHolder();
 AsyncCallback cb = new AsyncCallback(MyAsyncCallBack);
  IAsyncResult ar = dlgt.BeginInvoke(issueGroupId, element.ControlType, (EvaluatingEntityCombo.SelectedItem as CIQHydCore.RefData.RefDataInfo).Id, (IssuingEntityCombo.SelectedItem as CIQHydCore.RefData.RefDataInfo).Id, str1, str2,**cb,dlgt**);

MyAsyncCallBack 関数では、最後から取得した値を datgridview に入力する必要があります

于 2012-05-18T08:34:02.860 に答える