2

委任されたタスクを別の関数で分離する代わりにインライン化する方法はありますか?

元のコード:

    private void ofdAttachment_FileOk(object sender, CancelEventArgs e)
    {            
        System.Threading.ThreadPool.QueueUserWorkItem((o) => Attach());
    }

    void Attach() // I want to inline this function on FileOk event
    {

        if (this.InvokeRequired)
        {
            this.Invoke(new Action(Attach));
        }
        else
        {
            // attaching routine here
        }
    }

このようにしたかったのです(別の関数を作成する必要はありません):

    private void ofdAttachment_FileOk(object sender, CancelEventArgs e)
    {

        Action attach = delegate
        {
            if (this.InvokeRequired)
            {
                // but it has compilation here
                // "Use of unassigned local variable 'attach'"
                this.Invoke(new Action(attach)); 
            }
            else
            {
                // attaching routine here
            }
        };

        System.Threading.ThreadPool.QueueUserWorkItem((o) => attach());
    }
4

2 に答える 2

4

私はこれがうまくいくと思います:

private void ofdAttachment_FileOk(object sender, CancelEventArgs e)
{

    Action attach = null;
    attach = delegate
    {
        if (this.InvokeRequired)
        {
            // since we assigned null, we'll be ok, and the automatic
            // closure generated by the compiler will make sure the value is here when
            // we need it.
            this.Invoke(new Action(attach)); 
        }
        else
        {
            // attaching routine here
        }
    };

    System.Threading.ThreadPool.QueueUserWorkItem((o) => attach());
}

必要なのは、匿名メソッドを宣言する行の前にある 'attach' (null が機能する) に値を割り当てることだけです。ただ、前者の方が分かりやすいと思います。

于 2009-06-26T03:31:19.490 に答える
0

「未割り当て変数の使用」エラーが発生する理由は、コンパイラが実際にコードを生成する方法が原因です。デリゲート{}構文を使用すると、コンパイラによって実際のメソッドが作成されます。デリゲートの添付フィールドを参照しているため、コンパイラはローカル変数attachを生成されたデリゲートメソッドに渡そうとします。

これは、より明確にするのに役立つ大まかに翻訳されたコードです。

private void ofdAttachment_FileOk(object sender, CancelEventArgs e)
{

    Action attach = _b<>_1( attach );

    System.Threading.ThreadPool.QueueUserWorkItem((o) => attach());
}

private Action _b<>_1( Action attach )
{
    if (this.InvokeRequired)
    {
        // but it has compilation here
        // "Use of unassigned local variable 'attach'"
        this.Invoke(new Action(attach)); 
    }
    else
    {
        // attaching routine here
    }
}

初期化される前に、アタッチフィールドが_b<>_1メソッドに渡されていることに注意してください。

于 2009-06-26T04:51:48.870 に答える