做数据库操作时线程是否阻塞?
Is the thread blocked when doing database operation?
我们有一个 WCF 服务(部署在 IIS 上)对数据库进行昂贵的调用。它不使用任何类型的异步编程 (async\await)。
using (SqlDataAdapter adapter = new SqlDataAdapter())
{
using (SqlCommand command = new SqlCommand())
{
command.CommandType = CommandType.StoredProcedure;
command.CommandText = "StoreProcedure_NAME"; //Takes 6 seconds
command.Connection = connection;
adapter.SelectCommand = command;
adapter.Fill(dataset);
return dataset;
}
}
现在,在 6 秒的等待时间内调用数据库的线程(我相信这是一个 wcf 线程池线程)会发生什么情况。此线程是否阻塞并占用 CPU 个周期或线程是否处于等待状态(等待中断)?
是的,它被阻止了。有 async
方法旨在 return 线程到监听池,并在任务完成时从线程池中检索一个新的(或相同的)线程。非 async
方法将阻塞您的调用线程。
Is this thread blocking and taking up CPU cycles or will thread be in
waiting state (waiting for an interrupt)?
它正在等待中断并且不消耗任何 CPU 周期。当您发出 IO 请求时,该请求会一直向下传递到相关的设备驱动程序(或您的情况下的数据库进程),这本质上是异步的。这些IO请求通常注册一个IRP(IO请求包)。在数据库的情况下,线程将阻塞并等待中断以便恢复。
SqlAdapter
只是使用 Task Asynchronous Pattern
使用 SqlDataReader
(it's synchronous API, at least), which internally does expose asynchronous methods such as ReadAsync
and NextResultAsync
的包装器。与其不必要地启动一个新线程,不如使用那些 API。
我们有一个 WCF 服务(部署在 IIS 上)对数据库进行昂贵的调用。它不使用任何类型的异步编程 (async\await)。
using (SqlDataAdapter adapter = new SqlDataAdapter())
{
using (SqlCommand command = new SqlCommand())
{
command.CommandType = CommandType.StoredProcedure;
command.CommandText = "StoreProcedure_NAME"; //Takes 6 seconds
command.Connection = connection;
adapter.SelectCommand = command;
adapter.Fill(dataset);
return dataset;
}
}
现在,在 6 秒的等待时间内调用数据库的线程(我相信这是一个 wcf 线程池线程)会发生什么情况。此线程是否阻塞并占用 CPU 个周期或线程是否处于等待状态(等待中断)?
是的,它被阻止了。有 async
方法旨在 return 线程到监听池,并在任务完成时从线程池中检索一个新的(或相同的)线程。非 async
方法将阻塞您的调用线程。
Is this thread blocking and taking up CPU cycles or will thread be in waiting state (waiting for an interrupt)?
它正在等待中断并且不消耗任何 CPU 周期。当您发出 IO 请求时,该请求会一直向下传递到相关的设备驱动程序(或您的情况下的数据库进程),这本质上是异步的。这些IO请求通常注册一个IRP(IO请求包)。在数据库的情况下,线程将阻塞并等待中断以便恢复。
SqlAdapter
只是使用 Task Asynchronous Pattern
使用 SqlDataReader
(it's synchronous API, at least), which internally does expose asynchronous methods such as ReadAsync
and NextResultAsync
的包装器。与其不必要地启动一个新线程,不如使用那些 API。