十进制转字符串 "Specified cast is not valid"
Decimal to String "Specified cast is not valid"
private void comboBox4_SelectedIndexChanged(object sender, EventArgs e)
{
SqlCommand cmd = new SqlCommand(@"Select * FROM PRODUCTS where [PRODUCT CODE] = '" + comboBox4.Text + "'", con);
SqlDataReader myReader;
try
{
con.Open();
myReader = cmd.ExecuteReader();
while (myReader.Read())
{
int decimPRICE = myReader.GetInt32(myReader.GetOrdinal("PRICE"));
string PRICE = decimPRICE.ToString("0.00");
textBox7.Text = PRICE;
}
con.Close();
}
catch (Exception exe)
{
MessageBox.Show(exe.Message);
}
}
它在 ComboBox 到 Textbox
这个代码没问题,但是当我点击 item/index 时出现“Specified cast is not valid” =18=]组合框。不知道为什么。
decimPRICE 是价格(十进制 18,2)。
听起来你可能只是想要:
decimal price = reader.GetDecimal(reader.GetOrdinal("PRICE"));
textBox7.Text = price.ToString("0.00");
基本上,decimal
和 int
不是一回事,如果您将一个值存储为小数,您几乎肯定不想在小数点.
此外,现在我们可以看到您的更多代码,您应该立即停止这样做:
// WARNING! WARNING! SQL INJECTION ATTACK!
SqlCommand cmd = new SqlCommand(@"Select * FROM PRODUCTS where [PRODUCT CODE] = '" + comboBox4.Text + "'", con);
这容易受到 SQL Injection Attacks 的攻击 - 您应该改用参数化的 SQL:
SqlCommand cmd = new SqlCommand("Select * FROM PRODUCTS where [PRODUCT CODE] = @code, con);
cmd.Parameters.Add("@code", SqlDbType.Varchar).Value = comboBox4.Text;
这应该是您要更改的第一件事 - 目前这是一个 巨大的 安全漏洞。
你应该也每次都打开新的连接,并且在using
语句中有它(和命令,以及reader)所以他们妥善处理。
接下来,如果有多个匹配的产品,您实际上只使用最后一个结果 - 这是您想要的吗?
接下来,您只使用价格 - 为什么要使用 SELECT *
?
最后,这看起来像 WinForms GUI 或类似的 - 在这种情况下,您不应该在 UI 线程中执行此操作。任何长运行的工作都应该在单独的线程中完成,或者使用异步操作。
你应该这样使用 GetDecimal
:
decimal decimPRICE = myReader.GetDecimal(myReader.GetOrdinal("PRICE"));
string PRICE = decimPRICE.ToString("0.00");
textBox7.Text = PRICE;
请注意 decimPRICE
现在是 decimal
而不是 int
。
出现异常是因为 GetInt32
无法将 DB 小数转换为 Int32
。
private void comboBox4_SelectedIndexChanged(object sender, EventArgs e)
{
SqlCommand cmd = new SqlCommand(@"Select * FROM PRODUCTS where [PRODUCT CODE] = '" + comboBox4.Text + "'", con);
SqlDataReader myReader;
try
{
con.Open();
myReader = cmd.ExecuteReader();
while (myReader.Read())
{
int decimPRICE = myReader.GetInt32(myReader.GetOrdinal("PRICE"));
string PRICE = decimPRICE.ToString("0.00");
textBox7.Text = PRICE;
}
con.Close();
}
catch (Exception exe)
{
MessageBox.Show(exe.Message);
}
}
它在 ComboBox 到 Textbox
这个代码没问题,但是当我点击 item/index 时出现“Specified cast is not valid” =18=]组合框。不知道为什么。
decimPRICE 是价格(十进制 18,2)。
听起来你可能只是想要:
decimal price = reader.GetDecimal(reader.GetOrdinal("PRICE"));
textBox7.Text = price.ToString("0.00");
基本上,decimal
和 int
不是一回事,如果您将一个值存储为小数,您几乎肯定不想在小数点.
此外,现在我们可以看到您的更多代码,您应该立即停止这样做:
// WARNING! WARNING! SQL INJECTION ATTACK!
SqlCommand cmd = new SqlCommand(@"Select * FROM PRODUCTS where [PRODUCT CODE] = '" + comboBox4.Text + "'", con);
这容易受到 SQL Injection Attacks 的攻击 - 您应该改用参数化的 SQL:
SqlCommand cmd = new SqlCommand("Select * FROM PRODUCTS where [PRODUCT CODE] = @code, con);
cmd.Parameters.Add("@code", SqlDbType.Varchar).Value = comboBox4.Text;
这应该是您要更改的第一件事 - 目前这是一个 巨大的 安全漏洞。
你应该也每次都打开新的连接,并且在using
语句中有它(和命令,以及reader)所以他们妥善处理。
接下来,如果有多个匹配的产品,您实际上只使用最后一个结果 - 这是您想要的吗?
接下来,您只使用价格 - 为什么要使用 SELECT *
?
最后,这看起来像 WinForms GUI 或类似的 - 在这种情况下,您不应该在 UI 线程中执行此操作。任何长运行的工作都应该在单独的线程中完成,或者使用异步操作。
你应该这样使用 GetDecimal
:
decimal decimPRICE = myReader.GetDecimal(myReader.GetOrdinal("PRICE"));
string PRICE = decimPRICE.ToString("0.00");
textBox7.Text = PRICE;
请注意 decimPRICE
现在是 decimal
而不是 int
。
出现异常是因为 GetInt32
无法将 DB 小数转换为 Int32
。