如何使用LINQ计算List<T>中decimal类型Odds属性的乘积?
计算List中Odds属性的乘积
嗨,你说得没错,LINQ标准库确实没有内置的Product方法来直接计算集合元素的乘积,但我们有两种很方便的解决办法,完全可以像用Sum一样轻松实现需求!
方法一:自定义LINQ扩展方法(推荐复用场景)
我们可以自己写一个扩展方法,让它和Sum、Where这些LINQ方法一样好用。只需要创建一个静态类,添加下面的方法:
public static class EnumerableExtensions { public static decimal Product<TSource>(this IEnumerable<TSource> source, Func<TSource, decimal> selector) { // 空参数校验 if (source == null) throw new ArgumentNullException(nameof(source)); if (selector == null) throw new ArgumentNullException(nameof(selector)); decimal product = 1m; // 乘积的初始值是1(数学上的乘法单位元) foreach (var item in source) { product *= selector(item); } return product; } }
使用方式
写完扩展方法后,你就能像调用Sum一样调用它了:
decimal oddsProduct = myList.Product(x => x.Odds);
边界情况处理
- 如果集合是空的,这个方法会返回
1m,这符合数学上“空序列乘积为1”的定义(就像空序列求和为0一样)。 - 如果你需要空序列抛出异常,可以在方法开头添加检查:
if (!source.Any()) throw new InvalidOperationException("序列不包含任何元素,无法计算乘积。"); - 如果你担心decimal溢出问题,可以用
checked块包裹乘法逻辑,溢出时会抛出OverflowException:checked { product *= selector(item); }
方法二:直接使用Aggregate方法(快捷临时场景)
如果你不想额外写扩展类,也可以用LINQ的Aggregate方法直接实现,一行代码搞定:
decimal oddsProduct = myList.Aggregate(1m, (accumulator, currentItem) => accumulator * currentItem.Odds);
Aggregate的作用就是用一个累加器逐步计算:初始值设为1m,然后依次把累加器和每个元素的Odds相乘,最终得到乘积。
内容的提问来源于stack exchange,提问作者L. Page
相关产品推荐
相关产品推荐

