这两天从FreeSql转SqlSugar,记录一些日常

添加引用

<PackageReference Include="MySql.Data" Version="8.0.28" />
<PackageReference Include="SqlSugarCore" Version="5.0.5.4" />

上下文类

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using SqlSugar;

namespace DataService.DbContext
{
    /// <summary>
    /// 数据库上下文类
    /// </summary>
    public static class SqlSugarContext
    {
        /// <summary>
        /// 获取连接实例
        /// </summary>
        /// <param name="services"></param>
        /// <param name="configuration"></param>
        public static void AddSqlsugarSetup(this IServiceCollection services, IConfiguration configuration, string dbName)
        {
            // SqlSugarScope在此处使用AOP无效
            SqlSugarScope sqlSugar = new SqlSugarScope(new ConnectionConfig()
            {
                ConnectionString = configuration.GetConnectionString(dbName),
                DbType = DbType.MySql,// 切换数据库类型
                IsAutoCloseConnection = true,// 自动释放数据务,如果存在事务,在事务结束后释放
                InitKeyType = InitKeyType.Attribute// 从实体特性中读取主键自增列信息
            });
            #region AOP
            // SQL执行前
            //sqlSugar.Aop.OnLogExecuting = (sql, pars) =>
            //{
            //    List<Dictionary<string, object>> result = new List<Dictionary<string, object>>();
            //    foreach (var row in pars)
            //    {
            //        Dictionary<string, object> value = new Dictionary<string, object>();
            //        value.Add(row.ParameterName, row.Value);
            //        result.Add(value);
            //    }
            //    Console.WriteLine("{0}|SQL执行语句:{1},参数:{2}", DateTime.Now, sql, JsonConvert.SerializeObject(result));
            //};
            // SQL执行完
            //sqlSugar.Aop.OnLogExecuted = (sql, pars) =>
            //{
            //    // 执行完了可以输出SQL执行时间 (OnLogExecutedDelegate)
            //    Console.WriteLine("{0}|SQL执行时间:{1}", DateTime.Now, sqlSugar.Ado.SqlExecutionTime.ToString());
            //};
            #endregion
            services.AddSingleton<ISqlSugarClient>(sqlSugar);// 这边是SqlSugarScope用AddSingleton
        }
    }
}

注入SqlSugar

//连接MySQL数据库,添加数据库上下文
builder.Services.AddSqlsugarSetup(builder.Configuration, "MySQLConnection");

appsettings.json添加本地数据库连接字符串

"ConnectionStrings": {
    "MySQLConnection": "server=127.0.0.1;uid=root;pwd=123456;port=3306;database=world;SslMode=None"
  }

今天本打算写一个树形结构的菜单层级处理,看到SqlSugar官方文档有自带的方法ToTree

简单使用一下,以下是数据库结构

实体类数据代码

using System.Collections.Generic;
using SqlSugar;

namespace DataModel.Table
{
    /// <summary>
    /// 菜单表
    /// </summary>
    [SugarTable("menuinfo")]
    public partial class MenuInfo
    {
        /// <summary>
        /// 主键
        /// </summary>
        [SugarColumn(IsPrimaryKey = true, IsIdentity = true)]
        public int Id { get; set; }

        /// <summary>
        /// 菜单名称
        /// </summary>
        public string MenuName { get; set; }

        /// <summary>
        /// 父级Id
        /// </summary>
        public int? ParentId { get; set; }

        /// <summary>
        /// 不验证数据库,做树形结构使用
        /// </summary>
        [SqlSugar.SugarColumn(IsIgnore = true)]
        public List<MenuInfo> Child { get; set; }
    }
}

示例代码

private readonly ISqlSugarClient _dbContext;
public HomeDataService(ISqlSugarClient dbContext)
{
    _dbContext = dbContext;
}
public void SqlSugarTest()
{
    //SqlSugar自带树形结构
    Stopwatch sw = new Stopwatch();
    sw.Start();
    var tree = _dbContext.Queryable<MenuInfo>().ToTree(s => s.Child, s => s.ParentId, 0);
    string json = JsonConvert.SerializeObject(tree);
    sw.Stop();
    //Linq自带Foreach实现递归遍历树形结构
    Stopwatch sw2 = new Stopwatch();
    sw2.Start();
    var list = _dbContext.Queryable<MenuInfo>().ToList();
    list.ForEach(s => s.Child = list.Where(x => x.ParentId == s.Id).ToList());
    var tree2 = list.Count > 0 ? list.Where(s => s.ParentId == list.OrderBy(s => s.ParentId).ToList().FirstOrDefault().ParentId).ToList() : null;
    string json2 = JsonConvert.SerializeObject(tree2);
    sw2.Stop();
    Console.WriteLine("SqlSugar耗时:{0}ms,数据:{1}", sw.ElapsedTicks / (decimal)Stopwatch.Frequency * 1000, json);//SqlSugar
    Console.WriteLine("Linq Foreach耗时:{0}ms,数据:{1}", sw2.ElapsedTicks / (decimal)Stopwatch.Frequency * 1000, json2);//Linq Foreach
}

运行五次并打印日志

SqlSugar耗时:14.0168000ms
Linq Foreach耗时:7.8033000ms
SqlSugar耗时:1.6285000ms
Linq Foreach耗时:1.0115000ms
SqlSugar耗时:0.8813000ms
Linq Foreach耗时:0.7391000ms
SqlSugar耗时:4.4206000ms
Linq Foreach耗时:4.1635000ms
SqlSugar耗时:1.015000ms
Linq Foreach耗时:0.8329000ms

结论:SqlSugar这个ToTree方法处理树形结构很方便,但性能优化不如原生Foreach


被这风吹散的人说Ta爱的不深,被这雨淋湿的人说Ta不会冷