使用LINQ获取序列的奇数/偶数部分

时间:2008-11-05 22:49:50

标签: c# linq

说我有一个所有Projects的列表,我按Category对它们进行分组:

var projectsByCat = from p in Projects
                    group p by p.Category into g
                    orderby g.Count() descending
                    select new { Category = g.Key, Projects = g };

现在我想将其显示为网页中的列表,首先我创建左侧div,其次是右侧div。我按每ProjectsCategory的顺序排序,以显示最Categories的{​​{1}} - 因此我想将Projects分成两部分 - 如果我把左边的所有“奇数”projectsByCat和右边的“偶数”类别,我想我会得到一个相当理智的观点。

所以我认为我可以做到这一点来获得Categories的奇数和偶数成员:

projectsByCat

它编译 - 但是,当我运行它时,我得到一个例外:

  

不支持的重载用于查询运算符'Where'。

我认为自从它首先编译后我就安全了。;)

有优雅的方法吗?而且,有一个优雅的解释为什么我的创造性使用var oddCategories = projectsByCat.Where((cat, index) => index % 2 != 0); var evenCategories = projectsByCat.Where((cat, index) => index % 2 == 0); 不起作用?

提前致谢!

7 个答案:

答案 0 :(得分:42)

如果您正在使用LINQ to SQL或LINQ to Entities,则应首先将结果完全实现到内存中:

var oddCategories  = projectsByCat.ToList().Where((c,i) => i % 2 != 0);
var evenCategories = projectsByCat.ToList().Where((c,i) => i % 2 == 0);

使用索引器迭代数据库上的结果是不可能的,而不使用游标,ORM框架可以

答案 1 :(得分:22)

请注意,对同一个查询调用.ToList()两次将查询数据库两次。

将结果缓存到中间列表中会更好,然后应用谓词过滤:

var projectsByCat =
    (from p in Projects
    group p by p.Category into g
    orderby g.Count() descending
    select new { Category = g.Key, Projects = g }).ToList();

var oddCategories = projectsByCat.Where((cat, index) => index % 2 != 0);
var evenCategories = projectsByCat.Where((cat, index) => index % 2 == 0);

答案 2 :(得分:7)

oddCategories和evenCategories是落后的。

索引开始为0而不是1

0%2 = 0

0指数是奇数。

var oddCategories  = projectsByCat.Where((cat, index) => index % 2 == 0);

var evenCategories = projectsByCat.Where((cat, index) => index % 2 != 0);

答案 3 :(得分:4)

使用LINQ执行此操作并避免输入多次枚举的正确方法是对每个项目是偶数还是奇数进行分组或类似。

使用Select加载mixes in an index加上ToLookup的重载的简单方法可以为您提供所需内容:

var oddsAndEvens = input
    .ToList() // if necessary to get from IQueryable to IEnumerable
    .Select((item, index) => new { isEven = index % 2 != 0, item })
    .ToLookup(
        i => i.isEven,
        i => i.item);

这将生成Lookup<TKey, TElement>数据结构following benefit

  

如果在集合中找不到密钥,则返回空序列。

这意味着在上面的LINQ查询之后你可以这样做:

var evens = oddsAndEvens[true];
var odds = oddsAndEvens[false];

答案 4 :(得分:1)

您可以使用linq在视图中分隔奇数和偶数。

//even 
@foreach (var item in Model.Where((item, index) => index % 2 == 0))
{
     //do the code
}

//odd
@foreach (var item in Model.Where((item, index) => index % 2 != 0))
{
     //do the code
}

答案 5 :(得分:0)

var text = "this is a test <string> to extract odd <index> values after split";
var parts = text.Split(new char[] { '<', '>' });
IEnumerable words = parts.Where(x => parts.ToList().IndexOf(x) % 2 == 1)

单词将包含“string”和“index”

答案 6 :(得分:0)

你可以找到没有foreach循环的偶数数字

static void Main(string[] args)
{
    List<int> lstnum = new List<int> { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

    List<int> lstresult = lstnum.FindAll(x => (x % 2) == 0);

    lstresult.ForEach(x => Console.WriteLine(x));
}