SqlSugar和.NET ADO的 SqlConnection是一样的,一个线程只能是一个实例,单实例跨线程使用是错误用法
在使用线程是下面的代码是正确用法
for (int i = 0; i < 100; i++)
{
Thread t = new Thread(new ThreadStart(() =>
{
var db = GetInstance();//在不同线程都会new出一个实例
}));
t.Start();
}SqlSugar写成变量很容易出现线程问题
改成属性就可以避免,因为一些初学者代码不严谨经常出错,下面会举例说明
正确用法1:属性每次会new新实例
public static SqlSugarClient Instance //注意当前方法的类不能是静态的 public static class这么写是错误的
{
get{ return new SqlSugarClient(XXX);};
}
//用法
var db = 类.Instance;
db.Queryable<T>().ToList();正确用法2:
public class 类{
public SqlSugarClient Instance
{
get{ return new SqlSugarClient(XXX);};
}
}
//用法
var db = new 类().Instance;
db.Queryable<T>().ToList();错误写法1
public static SqlSugarClient Instance= new SqlSugarClient (XXX);
错误写法2
//因为这儿是静态的就出错了
public static 类 Instance= new 类();
public class 类{
public SqlSugarClient Instance= new SqlSugarClient (XXX);
}
Instance.Db.Sqluery<T>().ToList();//这样SqlSugarClient只会是一个实例所以会出错
//如果这儿不写成静态的
public 类 Instance= new 类();
public class 上层类{
public static 类 类=new 类(); //这儿是静态的一样会出错
}
//所以不写成属性只要一层是静态的都会出问题注意:数据库未释放或者datareader已存在都是自已代码问题,我花了大量时间解释给一些初学者,所以这里重点提出来
SqlSugarClient db = new SqlSugarClient(new ConnectionConfig()
{
ConnectionString = Config.ConnectionString, //必填
DbType = DbType.SqlServer, //必填
IsAutoCloseConnection = true //默认SystemTable
});当参数IsAutoCloseConnection 设为true
每次执行操作都会执行 connection.close ,事务内特殊些,会在事务回滚或提交的的时候执行 connection.close
当参数IsAutoCloseConnection 设为false
需要用using(var db=getInstance()) 或者db.Ado.Dispose()或者db.Ado.Close()进行释放
db.dispose和using整个对象都不能使用 close释放掉下次还可以开始
当然了按我上面的代码来写是没有问题的,如果还有怀疑就自已去测试,当然很多人测试方式不对我来这里纠正一下
单线程测试
这种方式是OK的单线程进行测试保证你的对象是否成功释放掉
for (int i = 0; i < 10000; i++)
{
var db = GetInstance();
//操作
db.Queryable<T>().ToList();
}多线程测试
就要注意上面的的线程安全问题 ,然后还需要注意默认连接池的大小 例如默认是100
最好用并发工具进行测试因为工具是在一秒内进行了100次请求,这100次请求可能是每10毫秒一次,因为有释放机质 400的并发可能一点问题没有,单纯开线程的方式触发点在同一个时间直接超过连接池上限报错。
例如最大连接池是100 ,你的的程序处理时间是10MS,你的并发最多只能是100,超了一定会报错,你的程序处理1MS 就可以是1000并发
总结:要结合你的数据库操作的处理能力,和合理的并发数 ,和你同时开启连接对象的数量不超过 你的连接池上线。
连接池默认是100
还有数据库的sleep没有清空问题,这个是ado正常的机质,close只会将状态改为 sleep,sleep是处于休息状态,当有数据库连接创建的时候会找有没有 sleep的对象,如果有就叫醒当前sleep对象,没有新创建一个连接对象,所以这种机质的存在 sleep数量并不会无限增长
sleep如果空闲过多数据库会定时清理
2016 © donet5.comApache Licence 2.0