在C#中,我该如何处理Oracle Float类型?接收错误“算术运算导致溢出”

问题描述:

我正在使用通用方法从任何Oracle表中接收单个行,并使用下面的代码将其显示在datagridview中。但是,如果表中包含一个float类型的列,并且该值具有大量的小数位数,则会在下面的代码行中得到“算术运算导致溢出”:MyReader.GetValues(objCells);在C#中,我该如何处理Oracle Float类型?接收错误“算术运算导致溢出”

  oCmd.CommandText = "OTCMIADM.OTCMI_GUI.GET_ROW"; 
      oCmd.CommandType = CommandType.StoredProcedure; 
      oCmd.Parameters.Add("PI_TABLE_NAME", OracleDbType.Varchar2, 40).Value = cmbStagingTables.SelectedItem; 
      oCmd.Parameters.Add("PI_ROWID", OracleDbType.Varchar2, 40).Value = txtRowID.Text; 
      oCmd.Parameters.Add(new OracleParameter("PIO_CURSOR", OracleDbType.RefCursor)).Direction = ParameterDirection.Output; 

      oCmd.ExecuteNonQuery(); 

      // clear the datagrid in preperation for loading 
      dgvStagingTable.Columns.Clear(); 
      dgvStagingTable.Rows.Clear(); 

      using (OracleDataReader MyReader = oCmd.ExecuteReader()) 
      { 
       int ColumnCount = MyReader.FieldCount; 

       // add the column headers 
       DataGridViewColumn[] columns = new DataGridViewColumn[ColumnCount]; 
       for (int i = 0; i < columns.Length; ++i) 
       { 
        DataGridViewColumn column = new DataGridViewTextBoxColumn(); 
        column.FillWeight = 1; 
        column.HeaderText = MyReader.GetName(i); 
        column.Name = MyReader.GetName(i); 
        columns[i] = column; 
       } 
       dgvStagingTable.Columns.AddRange(columns); 

       // get the data and add the row 
       while (MyReader.Read()) 
       { 
        //get all row values into an array 
        object[] objCells = new object[ColumnCount]; 
        MyReader.GetValues(objCells); 
        //add array as a row to grid 
        dgvStagingTable.Rows.Add(objCells); 
       } 
      } 

堆栈跟踪显示: 在Oracle.DataAccess.Types.DecimalConv.GetDecimal(IntPtr的numCtx) 在Oracle.DataAccess.Client.OracleDataReader.GetDecimal(的Int32ⅰ) 在Oracle.DataAccess.Client。 OracleDataReader.GetValue(的Int32 I) 在Oracle.DataAccess.Client.OracleDataReader.GetValues(Object []对象的值)

所以我能看到为什么它导致错误(这是假设十进制转换);但我该如何解决这个问题?

我试图与加载数据之前明确设置的列的类型:

dgvStagingTable.Columns [ “TR_THROUGHPUT_TIME_NO”]的ValueType = typeof运算(字符串);

和其他几种类型,但没有任何区别。

任何帮助表示赞赏。

我最初建议使用OracleDbTypeEx(http://download.oracle.com/docs/html/E15167_01/OracleParameterClass.htm#CHDJHDGE)为您解决这个问题,这是错误的,所以这是一个新的建议。

所以我做了什么:

Create Table Testdecimalteable(
    Acol number(10) , 
    DecCol NUMBER(38,38) 
); 
/

Insert Into Testdecimalteable 
Select level,Level/(power(2,level)) 
    From Dual 
    Connect By Level < 100 ; 

/

Create or replace Procedure Testprocdecimal(Crs OUT Sys_Refcursor) 
AS 
Begin 
    Open Crs For 
    Select * 
     FROM Testdecimalteable ; 
END Testprocdecimal ; 

现在,这将让已知超越.NET一些数据。

然后.NET方面:

OracleConnection _conn = new OracleConnection(""); 
    _conn.Open(); 
    OracleCommand oCmd = new OracleCommand(); 
    oCmd.CommandText = "Testprocdecimal"; 

    oCmd.CommandType = CommandType.StoredProcedure; 
    oCmd.Connection = _conn; 

    OracleParameter crs = new OracleParameter(); 
    crs.OracleDbType = OracleDbType.RefCursor ; 
    crs.Direction = ParameterDirection.Output; 
    crs.ParameterName = "crs"; 
    oCmd.Parameters.Add(crs); 
    using (OracleDataReader MyReader = oCmd.ExecuteReader()) 
    { 
     int ColumnCount = MyReader.FieldCount; 
     // get the data and add the row 
     while (MyReader.Read()) 
     { 
      //MyReader.GetOracleValue(1).ToString() 
      Console.WriteLine(string.Format("{0}/{1}", MyReader.GetValue(0),MyReader.GetOracleValue(1).ToString() )); 


     } 
    } 

这一切都转换为字符串,但它会工作。

http://download-east.oracle.com/docs/html/A96160_01/features.htm#1048038

我刚才看过了你的初始查询再次,你是两次致电查询:

oCmd.ExecuteNonQuery(); 
... 
using (OracleDataReader MyReader = oCmd.ExecuteReader()) 

你不需要为ExecuteNonQuery; ExecuteReader执行sp

+0

感谢您指出被调用两次的查询。 你提出的解决方案工作;我简单地使用.GetOracleValue(i).ToString()在添加到datagridview之前对数组进行填充,作为一种享受! 再次感谢, D. – ValiantBoy 2010-07-23 12:31:45