首页 > 解决方案 > 创建通用 Linq 扩展方法以通过键“缝合”数据

问题描述

我有一系列课程(ID、名称、状态、讲师等)和另一个定价集合(CourseId、Price)。

我正在尝试编写一个 linq 扩展方法将这两者合并在一起,但我的反思有点生疏。我错过了什么?

这就是我想这样称呼它:

courses.SewData(pricing, p => p.Id, c => c.CourseId);

这是被调用的方法。我对 ToDictionary Line 有疑问。它没有编译。如何使用现有表达式创建字典

public static class DataExtension {
    public static IEnumerable<TParent> SewData<TParent, TChild>(this IList<TParent> parentCollection, IList<TChild> childCollection, Expression<Func<TParent, object>> parentProperty, Expression<Func<TChild, object>> childProperty) {

        var parentPropertyInfo = ReflectionHelper.GetProperty(parentProperty);
        var childPropertyInfo = ReflectionHelper.GetProperty(childProperty);

        var parentDict = parentCollection.ToDictionary(parentProperty, x => x); //need help here
        foreach (var child in childCollection) {
            var childId = childPropertyInfo.GetValue(child);
            var parentItem = parentDict[childId];
            
            //use reflection here to map properties by name
            

            
            yield return parentItem;
        }          
    }
}

标签: c#linqreflection

解决方案


我想说你不需要这部分的表达式和反射,你可以尝试这样的事情(还TKey为键类型添加了通用参数):

public static class DataExtension {
    public static IEnumerable<TParent> SewData<TParent, TChild, TKey>(
         this IList<TParent> parentCollection, 
         IList<TChild> childCollection, 
         Func<TParent, TKey> parentKeySelector, 
         Func<TChild, TKey> childKeySelector) {

        var parentDict = parentCollection.ToDictionary(parentKeySelector); 
        foreach (var child in childCollection) {
            var childId = childKeySelector(child);
            var parentItem = parentDict[childId];
            
            //use reflection here to map properties by name             
              
            yield return parentItem;
        }          
    }
}

如果您以后由于某些其他原因仍需要表达式,您可以使用Compile从.parentKeySelectorparentProperty


推荐阅读