AI岗实习疑难杂症小记(一些重要而小众的题目心得)——数据库(SQL Server)相 ...

打印 上一主题 下一主题

主题 1678|帖子 1678|积分 5034

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

x
提示:某上市公司AI岗实习过程中的一点学习心得(实习不断,更新不断!)
  
  

前言

某上市公司AI岗菜鸟实习过程中的一点学习记载,本篇记载实际业务实现过程中与 SQL Server数据库访问 相干的一些心得。本人主要使用C#语言,其它语言均可参考。

记载日期:2025.01.27
1. 数据入库流程

1.1 获取数据库链接



  • string server: 服务器IP(SQL Server中的服务器IP地点)
  • string database:数据库库名
  1. string connStr = ConnectionStringUtil.Get(server, database, out errMsg);
复制代码
1.2 构建并关联数据库实体类、本地映射类



  • 除注1外,别的部门可为固定写法。
  • 自定义实体类Entities,继承DbContext数据库上下文类。
  • OnModelCreating 方法是 DbContext 中的一个重要方法,用于配置实体和数据库之间的映射。

    • modelBuilder.Conventions.Remove<…>:这行代码移除了默认的命名约定。EF 默认会使用复数形式来命名数据库中的表,比方,假如你的实体类名是 table_A,EF 会尝试将数据库表命名为 table_As。
    • System.Data.Entity.ModelConfiguration.Conventions.PluralizingTableNameConvention 是 EF 中的一个默认约定,它会将表名转为复数形式。通过移除它,表名将使用实体类名的单数形式,即 table_A 表,而不是 table_As。

  • 构建本地实体类table_A,对应数据库中的table_A表。此中的各字段名、字段属性严格遵循table_A表布局。但是当表中存在有默认值的字段时,此字段在本地实体类中可以忽略不写,如ENTRYDATE、ENTRYTIME字段。

    • 本地实体类名table_A一样平常设为与实际表名相同,若差别,则必要恰当修改代码(见下)。

  • 注1:当仅对表举行查询操作时,此行可省略;当必要修改表,即增、删、改时,必须加上此行。
  1. public class Entities : DbContext
  2. {
  3.     public Entities(string conn)
  4.         : base(conn)
  5.     {
  6.         System.Data.Entity.Database.SetInitializer<Entities>(null);
  7.     }
  8.     protected override void OnModelCreating(DbModelBuilder modelBuilder)
  9.     {
  10.         modelBuilder.Conventions.Remove<System.Data.Entity.ModelConfiguration.Conventions.PluralizingTableNameConvention>();
  11.     }
  12.     public DbSet<table_A> table_A { get; set; }//注1
  13. }
  14. public partial class table_A
  15. {
  16.     public int ID { get; set; }
  17.     public Nullable<System.DateTime> TDATE { get; set; }
  18.     public string SYMBOL { get; set; }
  19.     public Nullable<double> Rate { get; set; }
  20.     //public Nullable<System.DateTime> ENTRYDATE { get; set; }
  21.     //public string ENTRYTIME { get; set; }
  22. }
复制代码


  • 当本地实体类名midTable_A与实际表名table_A差别时,加入[Table(“table_A”)]举行映射,此中"table_A"是实际数据库表名:
  1. public class Entities : DbContext
  2. {
  3.     public Entities(string conn)
  4.         : base(conn)
  5.     {
  6.         System.Data.Entity.Database.SetInitializer<Entities>(null);
  7.     }
  8.     protected override void OnModelCreating(DbModelBuilder modelBuilder)
  9.     {
  10.         modelBuilder.Conventions.Remove<System.Data.Entity.ModelConfiguration.Conventions.PluralizingTableNameConvention>();
  11.     }
  12.     public DbSet<midTable_A> midTable_A { get; set; }//注1
  13. }
  14. [Table("table_A")]
  15. public partial class midTable_A
  16. {
  17.     public int ID { get; set; }
  18.     public Nullable<System.DateTime> TDATE { get; set; }
  19.     public string SYMBOL { get; set; }
  20.     public Nullable<double> Rate { get; set; }
  21.     //public Nullable<System.DateTime> ENTRYDATE { get; set; }
  22.     //public string ENTRYTIME { get; set; }
  23. }
复制代码
1.3 查询



  • 此部门可为固定写法。
  • 将查询结果类型转为本地映射类列表,此中每一项代表一个table_A类型的对象,即表中的一条记载。
  • using 语句确保 entity 对象在使用完成后被正确开释(即调用 Dispose 方法开释资源)。
  1. public List<table_A> GetDataList(string sql, string connStr)
  2. {
  3.     using (Entities db = new Entities(connStr))
  4.     {
  5.         //sql = @"select * from table_A with (nolock) where SYMBOL = 'AAA'";
  6.         return db.Database.SqlQuery<table_A>(sql).ToList();
  7.     }
  8. }
复制代码
1.4 构建本地映射类对象



  • 方法1:
  1. table_A Model = new table_A();
  2. Model.TDATE = date;
  3. Model.SYMBOL = "AAA";
  4. //...
复制代码


  • 方法2:(常用)
  1. table_A Model = new table_A()
  2. {
  3.         TDATE = date,
  4.         SYMBOL = "AAA"
  5.         //...
  6. };
复制代码


  • 一样平常来说,ID字段是体系自带,不用显示赋值;数据库建表时有默认值的字段也不用显示赋值。
1.5 数据入库



  • 此部门可为固定写法。
  • .Add(model)将 model 对象添加到上下文的 table_A 表中。

    • Add 方法只是将对象标志为“待插入”,实际插入是在调用 SaveChanges 时完成。
    • entity.SaveChanges() 将上下文中挂起的全部更改(如插入、更新、删除等)应用到数据库。

  1. public void AddDatabaseTable(table_A model, string connStr)
  2. {
  3.     using (Entities db = new Entities(connStr))
  4.     {
  5.         db.table_A.Add(model);//此处的table_A即数据库实体类中定义的DBSet对象,即public DbSet<table_A> table_A { get; set; }。
  6.         db.SaveChanges();
  7.     }
  8. }
复制代码
1.6 数据更新



  • 使用到lamda表达式找到对应记载举行修改。
  1. public void UpdateTable(table_A model, string connStr)
  2. {
  3.    using (Entities db = new Entities(connStr))
  4.    {
  5.        db.table_A.First(item => item.ID == model.ID).SYMBOL = model.SYMBOL;//此处的table_A即数据库实体类中定义的DBSet对象,即public DbSet<table_A> table_A { get; set; }。
  6.        db.SaveChanges();
  7.    }
  8. }
复制代码

2. sql查询踩坑



  • 查询前先判断sql语句中字段值是否非空,若空则报错:
  1. if (string.IsNullOrEmpty(Name))
  2. {
  3.     continue;
  4. }
  5. string sql = $"select * from table_A with(nolock) where ID='{Id}' and name='{Name}'";
  6. return db.Database.SqlQuery<table_A>(sql).ToList();
复制代码


  • 当sql语句的字段值中出现单引号时,必要预先更换为两个单引号:(困扰我很久)
  1. string Name = Name.Replace("'","''");
  2. string sql = $"select * from table_A with(nolock) where ID='{Id}' and name='{Name}'";
  3. return db.Database.SqlQuery<table_A>(sql).ToList();
复制代码

3. 节约时间开销

3.1 批量入库



  • 假如有大量数据必要入数据库(比方上万行的excel表格),同时必要每条数据单独提取举行解析,再入库,若每行数据都分别入库,则会大量消耗时间。
  • 采用先存列表,再批量入库的方法。
  1. public static void DBHelp.BulkInsert<T>(IList<T> list, string connStr, string tableName);
复制代码
批量入库(不检测库中是否有此记载,直接入库):


  • list: 入库的数据聚集(本地映射类的列表)
  • connStr: 毗连字符串
  • tableName: 入库表名
3.2 批量查询



  • 假如在每次循环中都必要查询数据库,非常耗时,可以在进入循环前一次性批量查库,结果存为列表,供循环内部搜索,可以大大提高检索效率,若将查询结果存为字典,则进一步提高速率。
3.3 案例



  • 下面这篇博客使用一个简朴的案例,通过 “多次查库入库 → 批量(一次性)查库入库、list检索 → 字典检索” ,逐步提高检索效率。
   文本文档解析入库流程优化
  
总结

持续更新-ing,未完待续 ~

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
回复

使用道具 举报

0 个回复

正序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

大连密封材料

论坛元老
这个人很懒什么都没写!
快速回复 返回顶部 返回列表