我正在设置一个winform
,它将一个学生的名字,姓氏和学生ID放入一个名为sql
的{{1}}数据库中,并执行一个存储过程来搜索对于该学生,然后在按下搜索按钮时在college
中显示结果。每当我按下搜索按钮时,都会出现以下错误
“ Search2.exe中出现类型'System.TypeInitializationException'的第一次机会异常”。
我的程序正在跳过显示的DataGridView
块,并转到Try
语句。谁能告诉我为什么?
Catch
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Data.SqlClient;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace Search2
{
public partial class frmSearch : Form
{
public frmSearch()
{
InitializeComponent();
}
private void btnSearch_Click(object sender, EventArgs e)
{
string studid, fname, lname;
try
{
// get the values
fname = txtFname.Text.Trim();
lname = TxtLname.Text.Trim();
studid = txtStudentID.Text.Trim();
//instantiate datatier
Class1 astudent = new Class1();
DataSet ds = new DataSet();
ds = astudent.GetStudents(studid, fname, lname);
// populate the datagrid with dataset
dgvStudents.DataSource = ds.Tables[0];
}
catch (Exception ex)
{
}
}
private void frmSearch_Load(object sender, EventArgs e)
{
// TODO: This line of code loads data into the 'collegeDataSet.STUDENT' table. You can move, or remove it, as needed.
//this.sTUDENTTableAdapter.Fill(this.collegeDataSet.STUDENT);
}
}
}
答案 0 :(得分:3)
根据异常类型进行判断-TypeInitializationException
-我怀疑问题出在静态字段初始值设定项上:
static String connString = ConfigurationManager.ConnectionStrings["Data Source=EVEDELL17;Initial Catalog=College;Integrated Security=True"].ConnectionString;
static SqlConnection myConn = new SqlConnection(connString);
static System.Data.SqlClient.SqlCommand cmdString = new System.Data.SqlClient.SqlCommand();
那些初始化程序将在运行时第一次“触摸”其包含的类(Class1
)时运行。因为它们不在方法中,所以当它们失败时,编译器很难给出有用的堆栈跟踪。尝试用静态构造函数替换内联初始化程序:
static String connString;
static SqlConnection myConn;
static System.Data.SqlClient.SqlCommand cmdString;
static Class1() {
connString = ConfigurationManager.ConnectionStrings["Data Source=EVEDELL17;Initial Catalog=College;Integrated Security=True"].ConnectionString;
myConn = new SqlConnection(connString);
cmdString = new System.Data.SqlClient.SqlCommand();
}
我认为您将通过这种方式获得更好的错误消息。您还可以在构造函数中设置一个断点,以查看初始化期间发生的确切情况。
答案 1 :(得分:0)
Xander得到了我认为的答案:初始化这些静态字段时,某些东西“碰撞”。众所周知,静态/类型构造函数在传达异常方面很差:
https://docs.microsoft.com/en-us/dotnet/api/system.typeinitializationexception
但是,潜在的问题是模式之一。并且有几个问题。但是,您经常可以捏造这些部分以获取简单的学习示例。
一次性
SqlConnectons是Disposeable,因为它包含一些非托管资源。始终丢弃可丢弃物。我的个人规则是:
避免使用Globals / Static
静态变量是全局变量。在发明了这些之后,我们很快意识到使用其中一种是90%的可怕想法。 特别用于交换/共享数据。
尽管我走得更远,但从来没有一个静态字段可以写。 constant
和readonly
(运行时常量)应该是您曾经使用过的唯一静态变量。如果无法做到这一点,请不要使其静态。诸如连接字符串之类的东西在该规则上得到提升。如果您不能像这样标记它,请不要让它以静态开头。
在顶部,我创建一个类,结构或tupple。并将其实例分配给静态的readonly / constant变量。诸如连接字符串之类的东西既可以是实例变量,也可以在每次调用GetStudents
之类的函数时上交。实际上,Class1看起来很像数据库访问抽象。尤其是那些属于“请勿静态”规则的人。