You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何处理Excel模板导入的DataTable,按编号规整存入双数据库表?

我来帮你搞定这个按编号处理DataTable数据并存入数据库的问题,核心思路是按编号分组后依次处理,这样就能解决数据对齐的问题了,下面是具体的实现步骤和代码示例:

解决思路
  • 先把DataTable里的数据按编号分组,确保同一编号的培训和参与者数据绑定在一起
  • 按编号从小到大排序分组,保证处理顺序是编号1→编号2→...依次进行
  • 对每个分组,先处理该编号的培训详情数据,插入到培训详情表后获取关联ID,再遍历分组内的所有行处理参与者信息,关联培训ID存入参与者表
代码实现(C#示例)

首先要引用System.Linq命名空间,然后按以下逻辑编写代码:

// 1. 按编号分组并按编号升序排序,确保处理顺序正确
var groupedData = dtsel.AsEnumerable()
                       .GroupBy(row => row.Field<int>("编号")) // 这里假设编号是int类型,根据实际改为string等
                       .OrderBy(group => group.Key);

// 遍历每个编号分组
foreach (var numberGroup in groupedData)
{
    int trainingRecordId = 0;
    var firstRow = numberGroup.First(); // 假设同一编号的培训详情字段一致,取第一条即可

    // --- 第一步:插入培训详情到数据库 ---
    using (var conn = new SqlConnection("你的数据库连接字符串"))
    {
        conn.Open();
        // 使用事务保证数据一致性,避免培训详情插入成功但参与者插入失败的情况
        using (var transaction = conn.BeginTransaction())
        {
            try
            {
                // 构造培训详情的插入SQL(参数化避免SQL注入)
                string insertTrainingSql = @"
                    INSERT INTO 培训详情表 (编号, 培训名称, 培训时间, 培训地点)
                    VALUES (@Number, @TrainingName, @TrainingTime, @TrainingLocation);
                    SELECT SCOPE_IDENTITY(); -- 获取自增的培训ID
                ";

                using (var cmd = new SqlCommand(insertTrainingSql, conn, transaction))
                {
                    // 添加参数,根据你的Excel字段和数据库表字段调整
                    cmd.Parameters.AddWithValue("@Number", firstRow.Field<int>("编号"));
                    cmd.Parameters.AddWithValue("@TrainingName", firstRow.Field<string>("培训名称"));
                    cmd.Parameters.AddWithValue("@TrainingTime", firstRow.Field<DateTime>("培训时间"));
                    cmd.Parameters.AddWithValue("@TrainingLocation", firstRow.Field<string>("培训地点"));
                    // 其他培训详情字段...

                    // 执行插入并获取培训ID
                    trainingRecordId = Convert.ToInt32(cmd.ExecuteScalar());
                }

                // --- 第二步:插入当前编号下的所有参与者信息 ---
                string insertParticipantSql = @"
                    INSERT INTO 参与者信息表 (培训ID, 参与者姓名, 联系方式, 所属部门)
                    VALUES (@TrainingId, @ParticipantName, @Contact, @Department);
                ";

                foreach (var participantRow in numberGroup)
                {
                    using (var cmd = new SqlCommand(insertParticipantSql, conn, transaction))
                    {
                        cmd.Parameters.AddWithValue("@TrainingId", trainingRecordId);
                        cmd.Parameters.AddWithValue("@ParticipantName", participantRow.Field<string>("参与者姓名"));
                        cmd.Parameters.AddWithValue("@Contact", participantRow.Field<string>("联系方式"));
                        cmd.Parameters.AddWithValue("@Department", participantRow.Field<string>("所属部门"));
                        // 其他参与者字段...

                        cmd.ExecuteNonQuery();
                    }
                }

                // 提交事务
                transaction.Commit();
                Console.WriteLine($"编号{numberGroup.Key}的数据处理完成");
            }
            catch (Exception ex)
            {
                // 异常回滚事务
                transaction.Rollback();
                Console.WriteLine($"处理编号{numberGroup.Key}的数据失败:{ex.Message}");
                // 可以在这里添加日志记录等操作
                throw; // 可选:抛出异常让上层处理
            }
        }
    }
}
注意事项
  • 字段匹配:代码中的字段名称(比如"编号"、"培训名称")要和你的DataTable列名、数据库表字段完全一致,根据实际情况调整。
  • 数据类型:如果编号是字符串类型,把Field<int>改成Field<string>,同时调整SQL参数的类型。
  • 事务处理:示例中加入了事务,确保同一编号的培训详情和参与者数据要么都插入成功,要么都回滚,避免数据不一致。
  • 性能优化:如果数据量很大,可以考虑批量插入参与者信息,减少数据库连接次数,比如用SqlBulkCopy或者拼接批量插入SQL(注意保持参数化避免注入)。

内容的提问来源于stack exchange,提问作者user3074125

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.12 05:04:38