0

まず第一に、私はここで新しく、csharpで新しいです。CSharpを学習するためのいくつかの演習を行っている間、ちょうど疲れ果てました。「NullReferenceExceptionが処理されませんでした」というエラーが発生する理由を見つけることができません。

1)これを克服する方法は?私の研究によると、初期化に関連していますが、それを行うことができませんでした。私はデバッグして、すべてのボタンが取得する値がnull値になるのを監視しましたが、これが原因ですか?どうすれば解決できますか?何をすべきか?追加するコードはどれですか?

(***クラスの初期化と配列およびnullのものに関するすべての情報提供の知識は大歓迎です。私はすべてのポイントを学び、専門家になりたいです:Pそして人々はコードを最適化することもできます。すべての追加情報は大歓迎です。)

2)そして、なぜコンパイラはエラーを表示しないのに、コードの実行中にエラーが発生するのですか?

わかりました今、私はコードブローを持っています

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace temp1
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            Button[] btn = new Button[5];

            for (int i = 0; i < 5; i++)
            {
                btn[i] = new Button();
                btn[i].Width = 50;
                btn[i].Height = 50;
                flowLayoutPanel1.Controls.Add(btn[i]);
                btn[i].Click += new EventHandler(btn_Click);
            }
        }

        void btn_Click(object sender, EventArgs e)
        {
            Button[] btn = sender as Button[];
            btn[3].Text = "button name changed";  // here problems occurs
            //btn[3].BackColor = Color.Red;   // here problems occurs
            // btn[3].PerformClick();    // here problems occurs
        }
    }
}
4

4 に答える 4

3

そのはず:

void btn_Click(object sender, EventArgs e)
{
    Button btn = sender as Button;
    btn.Text = "button name changed";  // here problems occurs
}

送信者はボタン自体であり、配列ではありません

コメントによる更新:

次のようなことをする必要があります。

public partial class Form1 : Form
{
    private Button[] m_ButtonsArray;

    public Form1()
    {
        InitializeComponent();
    }

    private void Form1_Load(object sender, EventArgs e)
    {
        m_ButtonsArray = new Button[5];

        for (int i = 0; i < 5; i++)
        {
            m_ButtonsArray [i] = new Button();
            m_ButtonsArray [i].Width = 50;
            m_ButtonsArray [i].Height = 50;
            flowLayoutPanel1.Controls.Add(m_ButtonsArray [i]);
            m_ButtonsArray [i].Click += new EventHandler(btn_Click);
        }
    }

    void btn_Click(object sender, EventArgs e)
    {
        m_ButtonsArray[3].Text = "button name changed";  // here problems occurs
    }
}

更新-5番目のボタンがクリックされたときに2番目のボタンを変更します。

public partial class Form1 : Form
{
    private Button[] m_ButtonsArray;

    public Form1()
    {
        InitializeComponent();
    }

    private void Form1_Load(object sender, EventArgs e)
    {
        m_ButtonsArray = new Button[5];

        for (int i = 0; i < 5; i++)
        {
            m_ButtonsArray [i] = new Button();
            m_ButtonsArray [i].Width = 50;
            m_ButtonsArray [i].Height = 50
            m_ButtonsArray [i].Tag = i;;
            flowLayoutPanel1.Controls.Add(m_ButtonsArray [i]);
            m_ButtonsArray [i].Click += new EventHandler(btn_Click);
        }
    }

    void btn_Click(object sender, EventArgs e)
    {
        Button btn = (Button)sender;
        if (((int)btn.Tag) == 5)
        {
           m_ButtonsArray[2].Text = "your text here";
        }
    }
}

説明:ボタンを作成するとき、ボタンがクリックされたときにインデックスをタグとして追加します(ボタンはTagプロパティを持つインデックスを認識します)。送信者オブジェクトをチェックします-にキャストしてButton、に保持されているインデックスを探しTagます。値が5の場合Tag、2番目のボタンを参照し(参照できますm_ButtonsArray)、値を変更します

于 2012-06-25T11:19:39.360 に答える
1

あなたもそのように解くことができます...それはeyossiの解法ととても似ています

パブリック部分クラスForm1:フォーム{プライベート

public Form1()
{
    InitializeComponent();
}
Button[] m_Buttons = Array new Button[5];

private void Form1_Load(object sender, EventArgs e)
{
    for (int i = 0; i < 5; i++)
    {
        m_ButtonsArray [i] = new Button();
        m_ButtonsArray [i].Width = 50;
        m_ButtonsArray [i].Height = 50;
        flowLayoutPanel1.Controls.Add(m_ButtonsArray [i]);
        m_ButtonsArray [i].Click += new EventHandler(btn_Click);
    }
}

void btn_Click(object sender, EventArgs e)
{
    m_ButtonsArray[3].Text = "button name changed";  // here problems occurs
}

}

于 2012-06-25T14:08:33.030 に答える
0

このコードは問題が始まるところです:

Button[] btn = sender as Button[];

コンパイル時に、senderof型objectがsの配列にキャストされないことをコンパイラーに示すことはありませんButton。ただし、実行時には配列ではないため、そのようにキャストされません。それはただのButton

Button btn = sender as Button;

ハンドラーメソッド(btn_Click)は、すべてのボタンを同時に処理するのではなく、それぞれを個別に処理します。ボタンがクリックされると、そのボタン自体がハンドラーメソッドを呼び出します。

于 2012-06-25T11:21:35.073 に答える
0

(他の人は、この例外がスローされる理由をすでに正しく答えています)

オブジェクトから別のオブジェクトへのキャスト(を使用)を強制しているため、コンパイラはエラーを表示できませasん。コンパイラはオブジェクトが何であるかを知らないため、エラーが発生することを知ることができません。

コード内のメソッドを手動で呼び出し、最初の引数としてボタンの配列を渡すと、コードはクラッシュしません。

この場合の良い点は、asスローされた例外の代わりに標準のキャストを使用することでした。これは、null値を伝播させて後で失敗させるのではなく、はるかに明示的で正しい行で発生します。

コードに関する小さな注意点は、配列は役に立たないことです。配列はどこにも使用せず、ロード関数の実行が終了するとすぐにメモリから削除されます(正確には言えませんが、必要に応じてガベージコレクターについて読むことができます)。詳細)。

于 2012-06-25T11:26:14.503 に答える