Агрегатные функции в ADO.NET с функциональностью GROUP BY - PullRequest
2 голосов
/ 07 мая 2009

Это более прямой вопрос, вытекающий из более раннего более общего вопроса, который у меня был раньше , теперь, когда я трачу больше времени на изучение ADO.NET

Я хочу взять таблицу данных ADO.NET и выполнить эквивалент запроса SQL SELECT с агрегатными функциями (например, SUM) для некоторых столбцов, а для других столбцов задать значение GROUP BY. Затем я хочу взять результат и отобразить его в DataGrid.

Я понимаю, что могу создать DataView для DataTable, который содержит критерии фильтра и агрегатные функции. Но на странице MSDN в выражениях говорится, что

"Если вы используете одну таблицу для создания агрегата, функциональность группировки будет отсутствовать. Вместо этого все строки будут отображать одно и то же значение в столбце."

Как получить функциональность типа GROUP BY из ADO.NET, не записывая мою таблицу в отдельную базу данных и не выполняя там запрос? Есть ли способ сделать это путем создания или использования второй таблицы?

Ответы [ 4 ]

2 голосов
/ 07 мая 2009

Вы можете использовать способность группировки LINQ для достижения этой цели. Кроме того, вы можете привязать DataGrid к запросу LINQ, но данные будут только для чтения.

Поиск в сети для группировки LINQ должен привести вас туда, куда вы идете.

1 голос
/ 05 ноября 2010

Вот как это сделать с помощью .NET 3.x и выше (LINQ):

http://codecorner.galanter.net/2009/12/17/grouping-ado-net-datatable-using-linq/

А вот как это сделать, используя .NET 2.0 и ниже (стандарт ADP.NET)

http://codecorner.galanter.net/2009/04/20/group-by-and-aggregates-in-net-datatable/

1 голос
/ 07 мая 2009

Одним из способов решения этой проблемы является преобразование результата запроса linq в DataTable с использованием отражения. Вот пример. Если у вас есть DataTable, вы получите полный групповой доступ, пейджинг и т. Д. *

    private static System.Data.DataTable ObjectArrayToDataTable(object[] data)
    {
        System.Data.DataTable dt = new System.Data.DataTable();
        // if data is empty, return an empty table
        if (data.Length == 0) return dt;

        Type t = data[0].GetType();
        System.Reflection.PropertyInfo[] piList = t.GetProperties();

        foreach (System.Reflection.PropertyInfo p in piList)
        {
            dt.Columns.Add(new System.Data.DataColumn(p.Name, p.PropertyType));
        }

        object[] row = new object[piList.Length];

        foreach (object obj in data)
        {
            int i = 0;
            foreach (System.Reflection.PropertyInfo pi in piList)
            {
                row[i++] = pi.GetValue(obj, null);
            }
            dt.Rows.Add(row);
        }

        return dt;
    }

    internal static DataTable GetAllStoredFileDetailsByUserID(int userID)
    {
        var db = GetDataContext();
        object[] result;
        try
        {
            result = (from files in db.Files
                      where files.OwnerUserID == userID && files.IsThumbnail == false
                      select new
                      {
                          FileID = files.FileID,
                          Name = files.Name,
                          DateCreated = files.DateCreated,
                          Size = files.Size,
                          FileHits = (from act in db.FileWebActivities where act.FileID == files.FileID select act).Count()
                      }).ToArray();
        }
        catch (Exception)
        {
           //omitted
        }
        return ObjectArrayToDataTable(result);
    }
0 голосов
/ 12 октября 2009
...