0

I have a List with class name Product and I want to know the index of the element which has the maximum value?

class Product
{
    public int ProductNumber { get; set; }
    public int ProductSize { get; set; }
}

List<Product> productList = new List<Product>();

int Index = productList.Indexof(productList.Max(a => a.ProductSize)); 

I have tried this but it is not getting answer! And getting an error:

"Unable to Cast as Product"

Dmitry Bychenko
  • 149,892
  • 16
  • 136
  • 186
AJAY KUMAR
  • 79
  • 6
  • If perfomance is important, do something like `var indexOfMax = productList.Select((item, index) => new { item, index }).Aggregate((a, b) => a.item.ProductSize > b.item.ProductSize ? a : b).index;` – Evk May 11 '18 at 06:52

7 Answers7

2

You can first map each item so that each product is associated with its index, then order by descending and get the first item:

int Index = productList
    .Select((x, index) => new { Index = index, Product = x })
    .OrderByDescending(x => x.Product.ProductSize).First().Index;

You don't need another call to IndexOf!

Sweeper
  • 145,870
  • 17
  • 129
  • 225
1

You are looking for ArgMax which is not implemented in Linq but can be easily emulated via Aggregate:

  int Index = productList
    .Select((item, index) => new { item, index })
    .Aggregate((s, v) => v.item.ProductSize > s.item.ProductSize ? v : s)
    .index;
Dmitry Bychenko
  • 149,892
  • 16
  • 136
  • 186
0

The method Max will give you the maximum ProductSize, not an instance of Product. This is why you are receiving this error.

You could do it with OrderByDescending:

var item = productList.OrderByDescending(i => i.ProductSize).First();
int index = productList.IndexOf(item);
Marc
  • 3,739
  • 4
  • 19
  • 34
0

This requires a sort

var maxObject = productList.OrderByDescending(item => item.ProductSize).First();
var index = productList.IndexOf(maxObject);

There are other, easier ways to do this. For example: There is an extension method in MoreLINQ that does this.

See this question

Marco Siffert
  • 474
  • 1
  • 4
  • 14
0

Here is a solution with Enumerable.Range:

int index = Enumerable.Range(0, productList.Count)
                      .FirstOrDefault(i => productList[i].ProductSize == productList.Max(x => x.ProductSize));

DEMO HERE

Slaven Tojic
  • 2,760
  • 2
  • 11
  • 30
0

Assuming list is not empty:

productList.Indexof(productList.OrderByDescending(a => a.ProductSize).First());
Pablo notPicasso
  • 2,923
  • 3
  • 15
  • 22
-1

productList.Max(a=>a.ProductSize) will return max ProductSize value , not Product object. that condition should be in WHERE condition.

par
  • 969
  • 1
  • 10
  • 26