DataReader - hardcode ordinals?

前端 未结 6 2060
执念已碎
执念已碎 2021-01-11 10:29

When returning data from a DataReader I would typically use the ordinal reference on the DataReader to grab the relevant column:

if         


        
6条回答
  •  悲&欢浪女
    2021-01-11 10:36

    The string name lookup is much more expensive than the ordinal call, but more maintainable and less "fragile" than hard coding the ordinals. So here's how I've been doing it. It's the best of both worlds. I don't have to remember the ordinal values or care if the column order changes, but I get the performance benefits of using ordinals.

    var dr = command.ExecuteQuery();
    if (dr.HasRows)
    {
        //Get your ordinals here, before you run through the reader
        int ordinalColumn1 = dr.GetOrdinal("Column1");
        int ordinalColumn2 = dr.GetOrdinal("Column2");
        int ordinalColumn3 = dr.GetOrdinal("Column3");
    
        while(dr.Read())
        {
            // now access your columns by ordinal inside the Read loop. 
            //This is faster than doing a string column name lookup every time.
            Console.WriteLine("Column1 = " + dr.GetString(ordinalColumn1);
            Console.WriteLine("Column2 = " + dr.GetString(ordinalColumn2);
            Console.WriteLine("Column3 = " + dr.GetString(ordinalColumn3);
        }
    }
    

    Note: this only really makes sense for readers you expect to have a decent number of rows in. The GetOrdinal() calls are extra, and only pay for themselves if your combined savings from calling GetString(int ordinalNumber) in the loop are greater than the cost of calling GetOrdinal.

    Edit: missed the second part of this question. Regarding DBNull values, I've started writing extension methods that deal with that possibility. example: dr.GetDatetimeSafely() Within those extension methods, you can do whatever you need to feel confident you get the expected value back.

提交回复
热议问题