• Dapper学习


    上一篇, 提到Query<Test>查询的时候, 如果Test中包含自定义class, Dapper不会给自定义class完成映射, 而是直接给null, 其实是可以实现的, 答案就在下面的基本用法介绍中

     提到用法, 首先是要实现CURD, 这里先介绍Read吧.

    先上实体:

        public enum Gender
        { 
            男 = 0,
            女
        }
    
        public class Tch_Teacher
        {
            public int Id { get; set; }
    
            public Gender Sex { get; set; }
            
            public string Name { get; set; }
    
            public bool IsDoublePosition { get; set; }
    
            public DateTime CreateDate { get; set; }
        }
        public class Tch_Contact
        {
            public int Id { get; set; }
    
            public int TId { get; set; }
    
            public string Phone { get; set; }
    
            public string QQ { get; set; }
    
            public string Weixin { get; set; }
        }
        public class TeacherInfo
        {
            public Tch_Contact Contact { get; set; }
    
            public Tch_Teacher Teacher { get; set; }
        }

    一、一对一映射

    var sql = string.Empty;
    
    sql = "select Count(1) from tch_teacher where id>@Id limit 3;";
    Console.WriteLine(conn.Query<int>(sql, new { Id = 10 }));
    Console.WriteLine(conn.Query<string>(sql, new { Id = 1 }));
    
    sql = "select Sex, Id, Name, CreateDate, No from tch_teacher limit 3;";
    var list = conn.Query<Test>(sql);
    var list1 = conn.Query<object>(sql);
    var list2 = conn.Query<dynamic>(sql); Console.WriteLine(list.ToList().FirstOrDefault().Name);

    一对一映射还是蛮简单的, 不需要解释了,  这种写法, 就是前面提到的, 如果Tch_Teacher里面有一个Tch_Contact类型的属性, 那么在映射的时候, 这个属性会直接赋值为null

    二、一对多映射

    sql = @"select a.Id, a.Sex, a.Name, a.CreateDate, a.No, b.Id, b.Phone, b.QQ, 
    b.Weixin from tch_teacher a left join tch_contact b on a.Id = b.TId order by a.Id asc limit 3;
    "; //No这个字段, 在类中并没有 var list1 = conn.Query<Test, Tch_Contact, TeacherInfo>(sql, (a, b) => { TeacherInfo tInfo = new TeacherInfo(); if (a != null) { tInfo.Teacher = a; } if (b != null) { tInfo.Contact = b; } return tInfo; }); //}, null, null, true, "Id", null, null);

    此时, 返回的 List<TeacherInfo> 中, Teacher 和 Contact 都是有值的, 而不是直接给null, 当然, TeacherInfo中, 还可以有别的字段, 比如 public int No {get;set;},

    此时的No是能获取到值的. 其中的映射原理, 这里我就不再赘述了, 能看懂Dapper中一对一映射的原理, 一对多映射也就差不多了. 

     如果将 TeacherInfo类中Contact属性修改一下, 改成 List<Tch_Contact>类型, 那么怎样得到一个按 Tch_Teacher 分组的数据呢?

    通常情况下, 会想到两种办法:

    一种是上面这种办法, 先得到全部数据, 然后通过GroupBy方法, 进行分组, 也能得到那种分组数据, 但那并不理想, 这种方法我就不贴了.

      1. 得到的数据, 并不是我们想要的那种格式数据, 虽然也是分组的数据.

      2. 有重复项. Tch_Teacher并没有得到去除重复的功能. 虽然分了组, 但是每组中的数据, Tch_Teacher仍然是重复的.

     另一种, 就是通过一个中间变量来获取, 方法如下:

    sql = @"select a.Id, a.Sex, a.Name, a.CreateDate, a.No, b.Id, b.Phone, b.QQ, b.Weixin 
        from tch_teacher a left join tch_contact b on a.Id = b.TId order by a.Id asc limit 6;"; 
    var infos = new Dictionary<int, TeacherInfo>();
    var list1 = conn.Query<Test, Tch_Contact, TeacherInfo>(sql, (a, b) =>
    {
        TeacherInfo tInfo;
        if (!infos.TryGetValue(a.Id, out tInfo))
        {
            tInfo = new TeacherInfo();
            tInfo.Contact = new List<Tch_Contact>();
            tInfo.Teacher = a;
            infos.Add(a.Id, tInfo);
        }
        if (b != null)
        {
            infos[a.Id].Contact.Add(b);
        }
        return infos[a.Id];
    });

    使用字典项, 在其中进行一个规整操作, 去除重复的 Tch_Teacher信息, 把Tch_Contact进行规整分组. 而且, 得到的结果, 就直接是想要的结果

    public class TeacherInfo
    {
        public List<Tch_Contact> Contact { get; set; }
    
        public Tch_Teacher Teacher { get; set; }
    }

     话说回来, 至于最终使用哪种方法, 要根据具体使用需求来定, 总体来说, 都能达到效果. 方法无好坏, 只是使用场景不同. 

  • 相关阅读:
    关于JDK中自带的类加载器
    关于Spring框架
    关于Java JUC
    数据库-数据添加与删除-视图-索引-存储过程
    数据库-查询练习
    数据库-数据类型-数据库创建表的 约束以及 DDL操作
    数据库-多表连接查询
    数据库笔记整理-数据库概述-三大范式及数据库基本命令
    JAVA笔记整理-JAVA网络编程-TCP/UDP传输
    JAVA笔记整理-线程二
  • 原文地址:https://www.cnblogs.com/elvinle/p/6050365.html
Copyright © 2020-2023  润新知