Dkong
Dkong

Reputation: 2788

Return Anonymous Type from a function

Can I use an anonymous type as a return type in a Function, and then stuff that returned value into an array or collection of some sort whilst also adding an additional field to the new array/collection? excuse my pseudocode...

private var GetRowGroups(string columnName)
{
var groupQuery = from table in _dataSetDataTable.AsEnumerable()
                             group table by new { column1 = table[columnName] }
                                 into groupedTable
                                 select new
                                 {
                                     groupName = groupedTable.Key.column1,
                                     rowSpan = groupedTable.Count()
                                 };
    return groupQuery;

}

private void CreateListofRowGroups()
{
    var RowGroupList = new List<????>();
    RowGroupList.Add(GetRowGroups("col1"));
    RowGroupList.Add(GetRowGroups("col2"));
    RowGroupList.Add(GetRowGroups("col3"));

}

Upvotes: 28

Views: 45677

Answers (6)

KV Prajapati
KV Prajapati

Reputation: 94645

No you can't return an anonymous type from the method. For more info read this MSDN doc. Use class or struct instead of an anonymous type.

You should read blog post - Horrible grotty hack: returning an anonymous type instance

If you are using framework 4.0 then you can return List<dynamic> but be careful to access the properties of anonymous object.

private List<dynamic> GetRowGroups(string columnName)
{
var groupQuery = from table in _dataSetDataTable.AsEnumerable()
                             group table by new { column1 = table[columnName] }
                                 into groupedTable
                                 select new
                                 {
                                     groupName = groupedTable.Key.column1,
                                     rowSpan = groupedTable.Count()
                                 };
    return groupQuery.ToList<dynamic>();
}

Upvotes: 21

MakePeaceGreatAgain
MakePeaceGreatAgain

Reputation: 37000

From C#7 you can return a list of tuples:

private IEnumerable<(string, string)> GetRowGroups(string columnName)
{
    return from table in _dataSetDataTable.AsEnumerable()
           group table by new { column1 = table[columnName] }
           into groupedTable
           select (groupedTable.Key.column1, groupedTable.Count());
}

You can even give the members of the tuple names:

private IEnumerable<(string groupName, string rowSpan)> GetRowGroups(string columnName)
{
    return from table in _dataSetDataTable.AsEnumerable()
           group table by new { column1 = table[columnName] }
           into groupedTable
           select (groupedTable.Key.column1, groupedTable.Count());
}

However you need System.ValueTuple from the Nuget Package Manager.

Anyway I suggest to give things a clear name that includes what their purpose is, in particular when this is part of a public API. Having said this you should consider to create a class that holds those properties and return a list of that type.

Upvotes: 0

mellamokb
mellamokb

Reputation: 56769

This is a very popular question. In general you cannot return an anonymous type due to the requirement of strong typing. However there are a couple of workarounds.

  1. Create a simple type to represent the return value. (See here and here). Make it simple by generating from usage.
  2. Create a helper method to cast to the anonymous type using a sample instance for casting.

Upvotes: 21

Alex Z
Alex Z

Reputation: 1442

Just use and ArrayList

    public static ArrayList GetMembersItems(string ProjectGuid)
    {
        ArrayList items = new ArrayList(); 

              items.AddRange(yourVariable 
                        .Where(p => p.yourproperty == something)
                        .ToList());
            return items;
    }

Upvotes: 2

Plymouth223
Plymouth223

Reputation: 1925

Use object, not var. You'll have to use reflection to access the properties outside the scope of the anonymous type though.

i.e.

private object GetRowGroups(string columnName) 
...
var RowGroupList = new List<object>();
...

Upvotes: 1

Chris Fulstow
Chris Fulstow

Reputation: 41882

No, you can't return an anonymous type directly, but you can return it using an impromptu interface. Something like this:

public interface IMyInterface
{
    string GroupName { get;  }
    int RowSpan { get; }
}

private IEnumerable<IMyInterface> GetRowGroups()
{
    var list =
        from item in table
        select new
        {
            GroupName = groupedTable.Key.column1,
            RowSpan = groupedTable.Count()
        }
        .ActLike<IMyInterface>();

    return list;
}

Upvotes: 4

Related Questions