简体   繁体   中英

LINQ group by and select random element from each group

I have a set of questions, where each question has a "Group" property.

I would like to extract a set containing one random question from each group.

I've tried the following LINQ query:

_questions = _questions.GroupBy(q => q.Group)
                       .Select(g => g.ElementAt(new Random().Next(0, g.Count())))
                       .ToList();

But it looks like the random.Next value is only calculated once, so the same generated value is used on each group?

That's probably how it's supposed to work (or I'm missing something), but what do I do if I want to generate a new random number for each group when selecting an element from that group?

Obviously this can be solved "the hard way", but can I do it with a LINQ query?

Regards

That's simple.Just define your random instance outside of your query:

Random rnd = new Random();

Then use this rnd inside of your query:

_questions = _questions.GroupBy( q => q.Group )
             .Select( g => g.ElementAt(rnd.Next(0, g.Count())) ).ToList();

I felt the chosen answer, while giving a sensible solution, doesn't make clear the issue at hand, so I offer this description.

What is going on is that your code isn't running Next(...) only once, it is running new Random().Next(...) many times. This means each random number is from a new Random instance, and this been the cause of concern in many previous questions (eg this question (see Guffa's answer)). This appears to always yields the same result because...

  • The new Random instances being seeded by the time when created
  • They are created in a tight loop, so it all takes place quickly

...meaning that the seed is always the same, so you always generate the same random number.

The answer provided by Selman22 deals with this tidily, as it only creates a single Random instance, and so it is only seeded once, giving you the random numbers you expect when you call Next(...) .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM