简体   繁体   English

使用精巧的点网一对多插入

[英]one-to-many insert using dapper dot net

I have seen here 我在这里看过

How to insert an IEnumerable<T> collection with dapper-dot-net 如何使用dapper-dot-net插入IEnumerable <T>集合

how dapper is able to handle IEnumerable as an input param and dispatch multiple commands for each member of the collection. dapper如何将IEnumerable作为输入参数处理并为集合的每个成员调度多个命令。

In my case I have an IEnumerable<int> Categories and a int SurveyId and I want to insert this one-to-many relationship into a separate mapping table called SurveyCategories 就我而言,我有一个IEnumerable<int> Categories和一个int SurveyId ,我想将此一对多关系插入到一个单独的映射表中,该映射表称为SurveyCategories

Is there a LINQ extension that I could use to concatenate these Categories with the same SurveyId , similar to .Concat() ? 是否有一个LINQ扩展名,可用来将这些类别与相同的SurveyId串联在一起,类似于.Concat()

Or should I loop through the collection and build up a new list of objects with SurveyId and CategoryId properties? 还是应该遍历集合并使用SurveyId和CategoryId属性建立一个新的对象列表?

You could do one insert for the surveys, and then insert all the survey categories at once using the following linq query as the parameter: 您可以对调查进行一次插入,然后使用以下linq查询作为参数一次插入所有调查类别:

var allSurveyCategories = surveys.SelectMany(s =>
     s.Categories.Select(c => new{SurveyId = s.SurveyId, CategoryId = c}));

Here is what I have done so far, I changed the categories slightly to an int array called CategoryIds just due to how its being used in my system, but I could have done survey.Categories.Select(c => c.Id).Zip(... 到目前为止,这是我所做的事情,由于类别在我的系统中的使用方式,我将类别稍微更改为一个名为CategoryIds的int数组,但是我可以完成survey.Categories.Select(c => c.Id).Zip(...

// insert using source data from form post matching a ISurvey interface, where .Id will be 0
var surveyId = conn.Query<int>("INSERT ... " + 
                               "SELECT CAST(SCOPE_IDENTITY() AS INT)")
                               .First();

        if(source.CategoryIds != null && source.CategoryIds.Count() > 0) {
            var surveyCategories = source.CategoryIds
                    .Zip(
                        Enumerable.Repeat<int>(
                            surveyId,
                            source.CategoryIds.Count()
                        ),
                    (c, s) => new { SurveyID = s, CategoryID = c }
            );

            conn.Execute(@"INSERT INTO [SurveyCategories] " + 
                         "VALUES (@SurveyID, @CategoryID)", 
                         surveyCategories);
        }

UPDATE: Here is my new approach using SelectMany based on Eren's answer, the use of Enumerable.Repeat(..) is a bit of a hack but this is the only way I have been able to do the same thing so far. 更新:这是我根据Eren的回答使用SelectMany的新方法,使用Enumerable.Repeat(..)有点麻烦,但这是迄今为止我能够做同样事情的唯一方法。

    ...
        var surveyCategories = source.CategoryIds.SelectMany(
            s => Enumerable.Repeat(surveyId, 1),
            (c, s) => new { SurveyID = s, CategoryID = c });
    ...

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM