6

If I want to initialize a list of groupings, can I do this inline?

Update with context

I already know I cannot initialize an interface, but is there already an implementation built into dotnet?

I don't want to create my own implementation, because I am trying to refactor an existing private method into its own class which is public, thus I need to pass parameters in for unit testing.

void MyMethod(IList<IGrouping<int, MyObject>> objGroupings)

Currently I have resorted to initializing a list, then grouping by a key:

var fooList = new List<MyObject>
{
     new MyObject{ foo = 5 },
     new MyObject{ foo = 5 },
     new MyObject{ foo = 5 },
     new MyObject{ foo = 2 },
     new MyObject{ foo = 2 }
};

var fooGrouping = fooList.GroupBy(o => o.foo).ToList();
EdmundYeung99
  • 2,461
  • 4
  • 27
  • 43
  • http://stackoverflow.com/questions/5072955/is-it-possible-to-create-some-igrouping-object – Habib Mar 04 '14 at 18:26

3 Answers3

7

IGrouping is just an interface and cannot be initialised. If you want to use the inline initialisation, you need you initialise an object that implements IGrouping

David Pilkington
  • 13,528
  • 3
  • 41
  • 73
  • So there is no IGrouping implementation built into dotnet? – EdmundYeung99 Mar 04 '14 at 22:16
  • 1
    @EdmundYeung99 Taken from http://stackoverflow.com/questions/8507561/what-is-the-implementing-class-for-igrouping "As of .NET 4.0, there is no public type in the core .NET framework that implements System.Linq.IGrouping" – David Pilkington Mar 05 '14 at 04:53
3

I agree with @David Pilkington's answer. Here's a class I've written/used for this purpose in the past:

sealed class Grouping<TKey, TElement> : IGrouping<TKey, TElement>
{
    private readonly TKey m_key;
    private readonly IEnumerable<TElement> m_elements;

    public Grouping(TKey key, IEnumerable<TElement> elements)
    {
        if (elements == null)
            throw new ArgumentNullException("elements");

        m_key = key;
        m_elements = elements;
    }

    public TKey Key
    {
        get { return m_key; }
    }

    public IEnumerator<TElement> GetEnumerator()
    {
        return m_elements.GetEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        return GetEnumerator();
    }
}
Matt Smith
  • 17,026
  • 7
  • 53
  • 103
  • So why is this not built into dotnet? Most interfaces in the Linq libraries have an implementation... anyway thanks for this – EdmundYeung99 Mar 04 '14 at 22:40
-2

You can initialize a dictionary instead:

var dic = new Dictionary<string, int>()
{
    { "foo", 1 },
    { "bar", 2 },
};

If you concern of multiple values with the same key, use dictionary of list or values (choose the list's type which be more efficient for your code)

Shlomi Borovitz
  • 1,700
  • 9
  • 9
  • That's still not creating a `List>`. – Servy Mar 04 '14 at 18:37
  • Of course not. But it's functionally equivalent (accessing values, by keys). If it's for mock up, and you need the specific type, I think you'll have to create your type which implements IGrouping (initializer would work with any type which implements IEnuemrable, and has `Add` method). Or, you can create a simple list, and get the IGrouping with LINQ query... – Shlomi Borovitz Mar 04 '14 at 18:50
  • First off, no, it's not equivalent, as `IGrouping` is not a means of accessing values through keys. It can potentially be used in that way, but it doesn't have to be. Heck, `GroupBy` doesn't use it that way. `ToLookup` does. There is no logical need for a dictionary here. Additionally, a dictionary is *not* logically a mapping of one key to a sequence of values, it's a mapping of a key to a single value. Your comment has two valid approaches, but one is listed in the question itself, and the other is in another answer, so neither is adding anything new here. – Servy Mar 04 '14 at 18:53
  • @Servy , as I written in my answer _If you concern of multiple values with the same key, use dictionary of list or values (choose the list's type which be more efficient for your code)_ ... sorry for not repeating myself. IGrouping is an interface. It is not an implementation - and Its just grouping of values, under a key... same what I've suggested in my answer. – Shlomi Borovitz Mar 04 '14 at 19:28
  • You say that, but your answer doesn't show it. And the fact remains that your solution *is not an implementation of that interface*. It would need to be to answer the question. – Servy Mar 04 '14 at 19:29
  • What I said, is written **in** the answer. If you read half of it, you cant complain it's not answering the question. The answer suggest a different way to initialize an object, which may have some similar functionality. It may not be the "best" solution for the problem, but I believe that the best way to figure a solution for a problem - is oo look around it, not just strictly through it - so I suggesting things that may help. – Shlomi Borovitz Mar 04 '14 at 19:45
  • So it's not technically answering the question asked, it's not good design, it's not clearer, it's not a complete answer, it's not using tools for their intended purposes, it's wasteful of system resource, etc. All of these things come together to indicate that this is a very low quality answer. It's simply not *useful*, as an answer. I have indicated this through my votes, and chosen to explain them through my comments. You're completely entitled to want to keep the answer around anyway, if that's what you want to do. – Servy Mar 04 '14 at 19:50
  • What are you talking about? _it's not technically answering the question_ Life is a little bit more than "technically strictly something". _it's not clearer_ clearer for what? do you have a six sense, which let you know the exact problem? how can you know if it's clearer for the actual problem? how do you know their _intended purposes_ . _it's wasteful of system resource_ do you solve many problems in computer systems? – Shlomi Borovitz Mar 04 '14 at 20:07
  • If you had so - you would know that to declare it as "wasteful of system resource" is the waste of optional solutions. The person which asked the question, can judge how appropriate the solution for his actual problem... not you. – Shlomi Borovitz Mar 04 '14 at 20:08
  • It's not technically answering the question because the question is *specifically* asking for a way of creating a `List>`. This doesn't do that, thus it's not answering the question. As for clarity, as I said before, this is using a `Dictionary` when you don't actually intend to create a lookup. This is confusing. Dictionaries are for looking up values. It's wasting system resources in that you're creating a dictionary only to not actually use it as a dictionary. Dictionaries take time and resources to create. – Servy Mar 04 '14 at 20:15
  • SO is specifically designed such that the person asking the question is *not* the sole arbiter of whether or not an answer is good. A core principle of the site is that members of the community vote based on which answers they feel are useful or not useful. This is a major differentiating factor from this site's competition. The question author's view matters only a little bit more than any other member of the community. – Servy Mar 04 '14 at 20:16
  • _Dictionaries are for looking up values_ ... no.. not necessarily.. dictionaries, and any other types are for solving problems. If a dictionary solves a problem more easily, or efficiently (depends on the demands in hand) - then dictionary is for that problem. SO is designed for that, and for that there are votes (which you used). Someone else, might find this solution more appealing for **his** problem. maybe not (I do not have a sixth sense)... – Shlomi Borovitz Mar 04 '14 at 20:24
  • `Dictionary` is a tool designed to perform a specific task. Using a tool for a task that it was not designed for is sometimes possible, but it tends to result in code that is confusing to the reader (they'll be expecting you to use the dictionary to lookup values, as that's what it's built for), and also often result in more fragile and awkward code, because after all, you're not using a tool for the task at hand, just like trying to drive a nail with a shoe is awkward. You can do it, sure. It can *work*, but it's still a far less useful suggestion than "use a hammer". – Servy Mar 04 '14 at 20:27
  • _Dictionary is a tool designed to perform a specific task. [...] result in code that is confusing to the reader_ only if the reader assumes that any type is for specific task... if you use a type in a really creative way, comments and documentation are for the reader. not assumptions. actually.. assumptions are not for any one, unless your code does something in a very intuitive and simple way. maintainability is a demand to take into account when considering a solution. if you do, and the type in hand still appropriate - then it doesn't matter for what problem that type was designed for. – Shlomi Borovitz Mar 04 '14 at 20:48