提问人:Edan Fisher 提问时间:6/4/2016 更新时间:6/4/2016 访问量:4328
对象引用未设置为对象的实例?但事实果真如此?C# [重复]
Object reference not set to an instance of an object? But it is? C# [duplicate]
问:
新手编码员在这里。正在开发 Yahtzee 游戏,但无法弄清楚为什么我已经更正了它时会出现此错误(对象引用未设置为对象实例)。我的“form”对象是 null,即使我已经在类构造函数中声明了它的实例,并且出现了一条绿线,表示它没有被使用。
public partial class Form1: Form {
public Form1() {
InitializeComponent();
}
private Game game;
public void ShowMessage(string message) {
lblMessage.Text = message;
}
public void StartNewGame() {
game = new Game(this);
}
private void btnRoll_Click(object sender, EventArgs e) {
game.RollDice();
}
class Game {
private Form1 form;
public Game(Form1 form) {
form = new Form1();
}
public void RollDice() {
form.ShowMessage("blahblah");
}
“NullReferenceException”错误出现在窗体上。ShowMessage,我不知道为什么。我在游戏构造函数中声明了表单类的新实例,当玩家选择运行 StartNewGame 方法的 StartNewGame 时,该实例将运行。让它工作的最简单方法是简单地将“Form1 form”添加到 Game 类中 RollDice() 方法的参数中,然后添加 game。RollDice(this) 在 Form1 事件处理程序中。但是赋值的说明指南指出我们不应该这样做,我们要在 Game 的构造函数中初始化 Form1 对象。请帮助我是新手,不明白为什么会发生这种情况。
答:
在构造函数中使用它:Game Class
public Game(Form1 form)
{
this.form = form;
}
评论
您的问题是构造函数中的命名冲突:
public Game(Form1 form)
{
form = new Form1();
}
该参数与窗体级别变量同名。这意味着构造函数代码正在启动您传入的变量,而不是类级别的变量。您应该使用限定符引用表单变量,或者最好重命名它。new
this
一种常见的做法是为类级变量使用下划线前缀:
class Game
{
private Form1 _form;
public Game(Form1 form) {
_form = new Form1();
}
}
您正在创建一个新表单,而不是将传入的表单分配给其局部变量。
class Game {
private Form1 form;
public Game(Form1 form) {
*form = new Form1();*
}
public void RollDice() {
form.ShowMessage("blahblah");
}
您应该更改代码,以便将传入的表单分配给其局部变量,如下所示:
public Game(Form1 form) {
this.form = form;
}
然后它应该起作用。
不要让你的班级知道那个叫它的人。这确实限制了将来代码的可重用性,因为现在任何尝试使用该类的人都必须有一个要调用的方法。Game
Form
Form
Game
ShowMessage
相反,只需让您的方法返回一个字符串......RollDice
class Game
{
public void RollDice()
{
// do important 'roll dice' stuff...
return "blahblah";
}
}
然后适当地处理返回值。Form
private void btnRoll_Click(object sender, EventArgs e)
{
string message = game.RollDice();
lblMessage.Text = message;
}
这完全避免了将 传递给您的班级的需要,并避免了很多获得 .Form
Game
NullReferenceException
评论
StartNewGame