Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/80.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 将varchar转换为数据类型numeric时出现算术溢出错误。尝试从数据库中读取时,并非每次都会发生_C#_Sql_Math_Overflow - Fatal编程技术网

C# 将varchar转换为数据类型numeric时出现算术溢出错误。尝试从数据库中读取时,并非每次都会发生

C# 将varchar转换为数据类型numeric时出现算术溢出错误。尝试从数据库中读取时,并非每次都会发生,c#,sql,math,overflow,C#,Sql,Math,Overflow,我正在尝试从本地数据库读入并创建并返回一个对象。我的代码在调用它的前3次循环中运行良好,然后失败,给了我一个错误:算术溢出错误将varchar转换为数据类型numeric。我已经做了大量调试,错误被抛出到reader.Read()。据我所知,我没有在那里转换任何东西,我所有的研究都发现了这个错误的完全不同的来源。任何帮助都将不胜感激 System.Data.SqlClient.SqlDataReader reader; /*Initialize Variables*/ using

我正在尝试从本地数据库读入并创建并返回一个对象。我的代码在调用它的前3次循环中运行良好,然后失败,给了我一个错误:算术溢出错误将varchar转换为数据类型numeric。我已经做了大量调试,错误被抛出到reader.Read()。据我所知,我没有在那里转换任何东西,我所有的研究都发现了这个错误的完全不同的来源。任何帮助都将不胜感激

System.Data.SqlClient.SqlDataReader reader;
/*Initialize Variables*/
        using (SqlCommand cmd = GetCommand("SELECT * FROM tblInventoryItem where InvoiceID = " + InvoiceNumber))
        {
            //Do Work...
            try
            {
                cmd.Connection.Open();
                reader = cmd.ExecuteReader();

                InventoryItem i;
                NItem ni;
                InventoryDataRepository2 idr = new InventoryDataRepository2();

                while (reader.Read())
                {
                    //Create an instance of the object....
                    i = new InventoryItem();
                    ni = new NItem();

                    ni.ItemNumber = (string)reader["ItemNumber"];
                    InventoryItem invitem = (InventoryItem)idr.GetItem(ni.ItemNumber);
                    ni.Title = invitem.Item.Title;
                    ni.Model = invitem.Item.Model;
                    ni.RetailPrice = invitem.Item.RetailPrice;
                    ni.WholesalePrice = invitem.Item.WholesalePrice;
                    i.Item = ni;
                    i.Quantity = Convert.ToInt32(reader["Quantity"]);


                    allItems.Add(i);
                }
编辑:堆栈跟踪:

 at System.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
 at System.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
 at System.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj, Boolean callerHasConnectionLock, Boolean asyncClose)
 at System.Data.SqlClient.TdsParser.TryRun(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj, Boolean& dataReady)
 at System.Data.SqlClient.SqlDataReader.TryHasMoreRows(Boolean& moreRows)
 at System.Data.SqlClient.SqlDataReader.TryReadInternal(Boolean setTimeout, Boolean& more)
 at System.Data.SqlClient.SqlDataReader.Read()
 at NeweggDistributor.InventoryItemDataRepository.GetAllItemsInInvoice(String InvoiceNumber) in c:\Users\AJ\Documents\Visual Studio 2012\Projects\NeweggDistributor\NeweggDistributor\InventoryItemDataRepository.cs:line 90
 Arithmetic overflow error converting varchar to data type numeric.

我同意Eric J.我不相信Reader.Read()会抛出这样的错误。我看到的是,如果数据库中的Quantity字段是一个字符串,无法转换为整数,或者如果它在数据库中为null,因为null不能转换为任何整数,则可能引发这样的错误。其他可能是零售价格和批发商价格字段。也许您可以注释掉这些行,并确保在注释掉它们时不会出现相同的错误。然后可以一次一个地取消对每个字段的注释,测试每个字段一次是否有一个新字段

我的第一个猜测是
i.Quantity=Convert.ToInt32(reader[“Quantity”])正在尝试将varchar字段转换为int,而varchar字符串不是数字。我很少在这种情况下使用Convert.ToInt32或C#casting,因为它们可能会抛出意外的严重错误。我创建了一个单独的方法来转换我想要的内容,并向它传递一个默认值,如果无法执行转换,将返回该值。因此,我在转换方法中使用“defaultValue”参数。

您的查询是

SELECT * 
FROM tblInventoryItem 
WHERE InvoiceID = 1234
我猜数据库中的
InvoiceID
是一个varchar字段。 这意味着您要在where子句中将整数与varchar进行比较。隐式转换将查询更改为

SELECT * 
FROM tblInventoryItem 
WHERE CONVERT(int, InvoiceID) = 1234
如果数据库中的任何InvoiceID包含不适合整数的内容,则会出现错误

SELECT * 
FROM tblInventoryItem 
WHERE InvoiceID = 5000000000
算术溢出错误使invoiceid>2147483648成为最可能的原因

请注意,如果您的
InvoiceNumber
对于整数也太大,则不会发生此错误

SELECT * 
FROM tblInventoryItem 
WHERE InvoiceID = 5000000000
将工作,因为它已更改为

SELECT * 
FROM tblInventoryItem 
WHERE CONVERT(bigint, InvoiceID) = 5000000000
当然,解决方案是使用参数

command.CommandText = @"SELECT * " +
                      @"FROM tblInventoryItem " +
                      @"WHERE InvoiceID = @InvoiceNumber";
command.Parameters.Add("@InvoiceNumber", SqlDbType.VarChar).Value = InvoiceNumber;

(如果确定InvoiceID仅包含数字,也可以使用类型为
SqlDbtype.BigInt
的参数)

InvoiceID和InvoiceNumber的类型是什么?Reader.Read()不会引发该错误。也许您正在调试优化的代码?抛出此异常时的堆栈跟踪是什么;到处使用缩写会使代码更难阅读。由于IDE中的代码完成,您实际上不需要键入完整的变量名,因此实际上不需要更多的键入,但会产生更可读的代码。而且,当变量只在循环内部使用时,没有真正的理由在循环外部声明变量。如果您忘记(重新)初始化它们,就会导致可能出现的错误,污染循环外部的intellisense,并给读者留下可能在循环外部使用它们的印象。