Coder Perfect

Is it possible to extract the names of the columns from a SqlDataReader?


Can I retrieve the names of all the columns returned in my SqlDataReader after connecting to the database?

Asked by Blankman

Solution #1

var reader = cmd.ExecuteReader();

var columns = new List<string>();

for(int i=0;i<reader.FieldCount;i++)


var columns = Enumerable.Range(0, reader.FieldCount).Select(reader.GetName).ToList();

Answered by Rob Stevenson-Leggett

Solution #2

The SqlDataReader has a GetName function that takes the column index and returns the name of the column.

GetOrdinal, on the other hand, accepts a column name and returns the column index.

Answered by Stephen Wrighton

Solution #3

A DataReaper can provide you with the column names.

Here’s the crucial part:

  for (int col = 0; col < SqlReader.FieldCount; col++)
    Console.Write(SqlReader.GetName(col).ToString());         // Gets the column name
    Console.Write(SqlReader.GetFieldType(col).ToString());    // Gets the column type
    Console.Write(SqlReader.GetDataTypeName(col).ToString()); // Gets the column database type

Answered by Steven Lyons

Solution #4

It has already been mentioned. Just a LINQ response:

var columns = reader.GetSchemaTable().Rows
                                     .Select(r => (string)r["ColumnName"])


var columns = Enumerable.Range(0, reader.FieldCount)

The second one is significantly faster and cleaner. Even if GetSchemaTable is cached in the first approach, querying will be exceedingly sluggish.

Answered by nawfal

Solution #5

If you only want the column names, you can do it by typing:

List<string> columns = new List<string>();
using (SqlDataReader reader = cmd.ExecuteReader(CommandBehavior.SchemaOnly))
    DataTable dt = reader.GetSchemaTable();
    foreach (DataRow row in dt.Rows)

If you simply require one row, though, I recommend my AdoHelper addon. If you only have an one line query and don’t want to deal with data tables in your code, this feature is ideal. It returns a dictionary of column names and values that is case insensitive.

public static Dictionary<string, string> ExecuteCaseInsensitiveDictionary(string query, string connectionString, Dictionary<string, string> queryParams = null)
    Dictionary<string, string> CaseInsensitiveDictionary = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
        using (SqlConnection conn = new SqlConnection(connectionString))
            using (SqlCommand cmd = new SqlCommand())
                cmd.Connection = conn;
                cmd.CommandType = CommandType.Text;
                cmd.CommandText = query;

                // Add the parameters for the SelectCommand.
                if (queryParams != null)
                    foreach (var param in queryParams)
                        cmd.Parameters.AddWithValue(param.Key, param.Value);

                using (SqlDataReader reader = cmd.ExecuteReader())
                    DataTable dt = new DataTable();
                    foreach (DataRow row in dt.Rows)
                        foreach (DataColumn column in dt.Columns)
                            CaseInsensitiveDictionary.Add(column.ColumnName, row[column].ToString());
    catch (Exception ex)
        throw ex;
    return CaseInsensitiveDictionary;

Answered by Yakir Manor

Post is based on