stackoverflow新手,非常适合c#beginner
目前正在创建一个表单,该表单根据存储在数据库中的数据生成条形图。所选记录由pID(患者的ID)和tdate(测试日期)识别。这些值由用户可以选择的2个组合框决定。我遇到的问题是只有存储在数据库中的第一个和最后一个记录填充了条形图。
if (radioButtonTestResult.Checked)
{
foreach (var series in TestResultBarChart.Series)
{
series.Points.Clear();
}
string tdate = comboBox2.Text;
using (SqlConnection connection = new SqlConnection(@"Data Source= (LocalDB)\v11.0;AttachDbFilename=|DataDirectory|\MMSEDB.mdf;Integrated Security=True"))
{
connection.Open();
string sql = "SELECT T_CLOCK_SCORE,T_LANGUAGE_SCORE,T_RECALL_SCORE,T_REGISTRATION_SCORE,T_ORIENTATION _SCORE,T_TIME FROM TEST_RESULTS WHERE P_ID='" + pID + "' AND T_DATE='"+ tdate +"'";
using(SqlCommand command = new SqlCommand(sql, connection))
{
command.CommandTimeout = 3600;
using (SqlDataReader reader = command.ExecuteReader(CommandBehavior.SequentialAccess))
{
while (reader.Read())
{
MessageBox.Show("hello4");
String clockScoreString = reader["T_CLOCK_SCORE"].ToString();
MessageBox.Show(clockScoreString);
clockScore = Int32.Parse(clockScoreString);
String langScoreString = reader["T_LANGUAGE_SCORE"].ToString();
langScore = Int32.Parse(langScoreString);
String recallScoreString = reader["T_RECALL_SCORE"].ToString();
recallScore = Int32.Parse(recallScoreString);
String regScoreString = reader["T_REGISTRATION_SCORE"].ToString();
regScore = Int32.Parse(regScoreString);
String orientScoreString = reader["T_ORIENTATION_SCORE"].ToString();
orientScore = Int32.Parse(orientScoreString);
String timeScoreString = reader["T_TIME"].ToString();
timeScore = Int32.Parse(timeScoreString);
}
reader.Close();
}
}
this.TestResultBarChart.Series["Series1"].Points.AddXY("Clock Score", clockScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Language Score", langScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Recall Score", recallScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Registration Score", regScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Orientation Score", orientScore);
}
}
这是一张数据图: Test_results_table
这是第一个记录工作的界面图片: interface
我知道这与读者有关,但无法解决如何正常运作
非常感谢任何帮助
答案 0 :(得分:0)
您正在循环读取所有返回的值,然后退出循环并仅使用最后一个值来设置您的Points。您应该在循环中移动点设置
....
while (reader.Read())
{
clockScore = Convert.ToInt32(reader["T_CLOCK_SCORE"]);
langScore = Convert.ToInt32(reader["T_LANGUAGE_SCORE"]);
recallScore = Convert.ToInt32(reader["T_RECALL_SCORE"]);
regScore = Convert.ToInt32(reader["T_REGISTRATION_SCORE"]);
orientScore = Convert.ToInt32(reader["T_ORIENTATION_SCORE"]);
timeScore = Convert.ToInt32(reader["T_TIME"]);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Clock Score", clockScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Language Score", langScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Recall Score", recallScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Registration Score", regScore);
this.TestResultBarChart.Series["Series1"].Points.AddXY("Orientation Score", orientScore);
}
reader.Close();
请注意,您的查询是使用字符串连接构建的。这是数据库代码的众所周知的问题。永远不要这样做并使用parameterized query
修改强>
看看下面的评论,我重复建议使用参数化查询而不是字符串连接。这不仅避免了Sql Injection的攻击,而且你也不会让你的工作理解数值引擎的价值意义
DateTime tDate = Convert.ToDateTime(comboBox2.Text);
......
string sql = @"SELECT
T_CLOCK_SCORE,T_LANGUAGE_SCORE,T_RECALL_SCORE,
T_REGISTRATION_SCORE,T_ORIENTATION_SCORE,T_TIME
FROM TEST_RESULTS
WHERE P_ID=@id AND T_DATE=@date";
using(SqlCommand command = new SqlCommand(sql, connection))
{
command.Parameters.Add("@id", SqlDbType.Int).Value = pID;
command.Parameters.Add("@date", SqlDbType.Date).Value = tdate;
command.CommandTimeout = 3600;
using (SqlDataReader reader = command.ExecuteReader(CommandBehavior.SequentialAccess))
{
while (reader.Read())
....
在此示例中,我假设变量pID
的类型为整数,变量tDate
的类型为DateTime,与数据库字段的类型相匹配。这对数据库引擎没有任何疑问
当然,如果字段的类型不同,那么您应该相应地更改SqlDbType。