Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/324.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# 将TSQL转换为Linq转换为实体_C#_Entity Framework_Linq_Tsql_Linq To Entities - Fatal编程技术网

C# 将TSQL转换为Linq转换为实体

C# 将TSQL转换为Linq转换为实体,c#,entity-framework,linq,tsql,linq-to-entities,C#,Entity Framework,Linq,Tsql,Linq To Entities,我有两个名为FileList和ExtensionsCategory的表: FileList ------------------------------------------------------------- ID Path Extension 1 C:\7.pdf pdf 2 D:\3.png png 3 C:\1.mp3 mp3 4 D:\32.pdf pdf 及 表之间没有

我有两个名为FileList和ExtensionsCategory的表:

FileList
-------------------------------------------------------------
ID    Path         Extension

1     C:\7.pdf        pdf
2     D:\3.png        png
3     C:\1.mp3        mp3
4     D:\32.pdf       pdf

表之间没有任何关系

现在我想知道每个类别包含多少个文件? 我在SSMS中编写了以下TSQL查询,效果良好:

SELECT 
     Category
    ,SUM(FileCount) AS TotalFileCount 
FROM    
    (SELECT 
         COUNT(*) AS FileCount
        ,(SELECT ExtensionsCategories.Category FROM ExtensionsCategories WHERE FileList.Extension = ExtensionsCategories.Extension) AS Category
    FROM FileList GROUP BY Extension) AS T1 GROUP BY Category
我想知道有没有改进的方法可以在没有连接的情况下实现这一点

我尝试使用Linq to Entities编写它,这是我的代码,但我无法完成:

    var a = _dbContext.FileLists
        .Select(fl => new
        {
            Extension = fl.Extension,
            Count = _dbContext.FileLists.Count(),
            Cat =
                _dbContext.ExtensionsCategories.Where(w => w.Extension == fl.Extension).Select(s => s.Category)
        }).GroupBy(g => g.Extension);

这将为您提供正确的结果:-

var result = from f in _dbContext.FileLists
             group f by f.Extension into g
             let firstCategory = _dbContext.ExtensionsCategories
                                           .FirstOrDefault(x => x.Extension == g.Key)
             select new
                    {
                        Category = firstCategory != null ? firstCategory.Category : "",
                        TotalFileCount = g.Count()
                    };
或者,如果需要使用
方法语法
:-

var result = _dbContext.FileLists.GroupBy(e => e.Extension)
              .Select(x =>
                  {
                      var firstCategory = _dbContext.ExtensionsCategories
                                           .FirstOrDefault(z => z.Extension == x.Key);
                      return new
                        {
                           Category = firstCategory != null ? firstCategory.Category : "",
                           TotalFileCount = x.Count()
                        };
                  });
使用Linq到对象

更新:

如果类别可以包含多个扩展名,则可以使用以下查询:-

var result = extensionCat.GroupBy(x => x.Category)
                      .Select(x =>
                         new
                          {
                              Category = x.Key,
                              TotalFileCount = fileList.Count(f => x
                                                    .Any(z => z.Extension == f.Extension))
                          }
                      );

还有另一种方法可以更快地获得相同的结果

首先是
GroupBy
文件扩展名,然后在
GroupBy
元素选择器中对它们进行计数。在这里,您还可以获取密钥的类别名称,在本例中,这些密钥是文件扩展名:

var result =
    Files
    .GroupBy(x => x.Extension, (ext, fs) => new 
    { 
        Extension = ext, 
        Category = Categories.Single(c => c.Extension == ext).Name, 
        FileCount = fs.Count() 
    });
这将生成以下查询:

SELECT [t1].[Extension], (
    SELECT [t2].[Name]
    FROM [Category] AS [t2]
    WHERE [t2].[Extension] = [t1].[Extension]
    ) AS [Category], [t1].[value] AS [FileCount]
FROM (
    SELECT COUNT(*) AS [value], [t0].[Extension]
    FROM [File] AS [t0]
    GROUP BY [t0].[Extension]
    ) AS [t1]

@另一方面,拉胡辛格版本产生了以下结果:

-- Region Parameters
DECLARE @p0 NVarChar(1000) = ''
-- EndRegion
SELECT 
    (CASE 
        WHEN EXISTS(
            SELECT TOP (1) NULL AS [EMPTY]
            FROM [Category] AS [t2]
            WHERE [t2].[Extension] = [t1].[Extension]
            ) THEN (
            SELECT [t4].[Name]
            FROM (
                SELECT TOP (1) [t3].[Name]
                FROM [Category] AS [t3]
                WHERE [t3].[Extension] = [t1].[Extension]
                ) AS [t4]
            )
        ELSE CONVERT(NVarChar(50),@p0)
     END) AS [Category], (
    SELECT COUNT(*)
    FROM [File] AS [t5]
    WHERE (([t1].[Extension] IS NULL) AND ([t5].[Extension] IS NULL)) OR (([t1].[Extension] IS NOT NULL) AND ([t5].[Extension] IS NOT NULL) AND ([t1].[Extension] = [t5].[Extension]))
    ) AS [TotalFileCount]
FROM (
    SELECT [t0].[Extension]
    FROM [File] AS [t0]
    GROUP BY [t0].[Extension]
    ) AS [t1]

我用1.000.000行测试了这两个查询,结果如下:

ToList
版本相比:


在统计数据的最后几行中,您可以看到短版本大约快3倍。

@MojtabaTajik-哪些数据?抱歉,我忘记了广告链接:认为我们在同一类别中有多个扩展。@MojtabaTajik-好的,检查我的更新,它会起作用。已经更新了小提琴。@MojtabaTajik-嘿,我已经再次更新了代码,这将更简单,应该也可以与EF一起使用。
-- Region Parameters
DECLARE @p0 NVarChar(1000) = ''
-- EndRegion
SELECT 
    (CASE 
        WHEN EXISTS(
            SELECT TOP (1) NULL AS [EMPTY]
            FROM [Category] AS [t2]
            WHERE [t2].[Extension] = [t1].[Extension]
            ) THEN (
            SELECT [t4].[Name]
            FROM (
                SELECT TOP (1) [t3].[Name]
                FROM [Category] AS [t3]
                WHERE [t3].[Extension] = [t1].[Extension]
                ) AS [t4]
            )
        ELSE CONVERT(NVarChar(50),@p0)
     END) AS [Category], (
    SELECT COUNT(*)
    FROM [File] AS [t5]
    WHERE (([t1].[Extension] IS NULL) AND ([t5].[Extension] IS NULL)) OR (([t1].[Extension] IS NOT NULL) AND ([t5].[Extension] IS NOT NULL) AND ([t1].[Extension] = [t5].[Extension]))
    ) AS [TotalFileCount]
FROM (
    SELECT [t0].[Extension]
    FROM [File] AS [t0]
    GROUP BY [t0].[Extension]
    ) AS [t1]