0

は、ここに私の拡張メソッドです。 この作品:スレッド・セーフジェネリック拡張メソッドの使用法の構文問題

Action<DataGridView> a = row => row.DataSource = ds.bLog; 
this.dataGridView1.Invoke(a); 

これはコンパイルされません:

this.dataGridView1.Invoke<DataGridView>(o => o.DataSource = ds.bLog); 

とSystem.Windows.Forms.Controlが 'データソース' の定義が含まれていないと言う...

行います私は本当にこれを2行に分割しなければなりませんか? わかりやすいように、汎用拡張メソッドInvokeSafeを呼び出す必要がありますか?

編集:拡張メソッドは、(作品が、私は名前のデリゲートの要件を削除したい)改訂:

private delegate void myDel(); 

public static void InvokeSafe<T>(this T c, Action<T> DoWhat) where T : Control 
{ 
    myDel d = delegate() { DoWhat(c); }; 
    if (c.InvokeRequired) 
     c.Invoke(d); 
    else 
     DoWhat(c); 
} 

私はに係数アウトmyDelを作成する方法を見つけ出すように見えることはできませんブロック内の匿名の代理人?

+0

明らかに私はc.Invoke(o => DoWhat(c))で私の匿名の代理人を間違えています。それはコントロールの.Invoke(デリゲート)メソッドを呼び出さず、メソッドを再帰しているからです。 – Maslow

答えて

2

はにあなたのメソッドのシグネチャを変更してみてください。

+0

ありがとう、これは、偶然のスタックオーバーフロー、感謝を見つけるためにInvokeSafeにInvokeを変更することと組み合わせて、私が見逃していたキーでした。私がそれを正しく読んでいるなら、あなたはJonの前にあなたの答えを得て、もっと担当者を使うことができるので、私はこれを受け入れます。 – Maslow

+0

ちょうど指示のポイントとして、私の答えは2分前にジェイソンの前にあったが、私は本当に気にしない:) –

+0

@ジョン - 私はあなたが気にしないことを願った、私はそれらを後ろに読んでいると思うJon – Maslow

4

問題は、あなたのアクションは(メソッド内で)Controlでしか動作しないと宣言されていることです。このように変更します。

public static void Invoke<T>(this T c, Action<T> DoWhat) 
    where T:System.Windows.Forms.Control 
{ 
    if (c.InvokeRequired) 
     c.Invoke((EventHandler) delegate { DoWhat(c) }); 
    else 
     DoWhat(c); 
} 

その方法は、コンパイラはあなたがAction<DataGridView>がそう呼び出し側でのラムダ式はDataSourceを使用することができますしたいことを推測します。これはあなたのActionが指定した目的のタイプを使用できるようになる

public static void Invoke<T>(this T c, Action<T> DoWhat) 

+0

c.Invoke(o => DoWhat(c)); InvokeSafeに関数名を変更すると、その行は機能しなくなりました。 私はコントロールのInvokeを呼び出そうとしていますが、recurseではありません。 – Maslow

+0

なぜスタックオーバーフローですか?あなたが変更したコードの* only *部分がDoWhat変数の型であることを覚えておいてください。 –

+0

私のコードはまず悪かったからです。これは、コントロールの呼び出しメソッドの代わりに、自分自身を書かれたものとして呼び出すことでした。 – Maslow

0

さらに、Jon Saidは、データソースはSystem.Windows.Forms.Controlには存在しません。データソースはデータグリッドにあります。したがって、エラーメッセージを見ると、データソースを持たない型でデータソースを設定しようとしていることがわかります。 Jonが提案したことを実行することで問題を解決する必要があります。

0

作品!

public static void InvokeSafe<T>(this T c, Action<T> DoWhat) 
where T : System.Windows.Forms.Control 
    { 

     Action d = delegate() { DoWhat(c); }; 
     if (c.InvokeRequired) 
      c.Invoke(d); 
     else 
      DoWhat(c); 

    } 

このコードは有効ではありませんInvalidOperationException-クロススレッドとして動作しないが:

List<customer> c=new List<customer>{new customer{ Name="test"},new customer{Name= "John doe"}}; 
     Thread t = new Thread(o => this.dataGridView1.DataSource = c); 
     t.Start(); 

新しい拡張メソッドはしていません!

List<customer> c=new List<customer>{new customer{ Name="test"},new customer{Name= "John doe"}}; 
     Thread t = new Thread(o => this.dataGridView1.InvokeSafe(p => p.DataSource = c)); 
     t.Start(); 
+0

想像明示的なデリゲートの初期化を除外する方法もありますが、私はそれに満足しています。 – Maslow