上一篇
如何用C快速统计数据库中各部门人员数量?
- 行业动态
- 2025-05-14
- 1
使用C#连接数据库,通过编写SQL查询语句统计各部门员工数量,借助SqlConnection执行聚合查询,利用GROUP BY对部门字段分组计数,将结果存储在DataTable中,最终通过界面控件或文件形式展示各部门人数统计数据,实现高效准确的人力资源统计功能。
环境配置
引用数据库驱动
通过NuGet安装对应包:Install-Package System.Data.SqlClient // SQL Server Install-Package MySql.Data // MySQL
数据库表结构示例
CREATE TABLE Departments ( DeptID INT PRIMARY KEY, DeptName NVARCHAR(50) NOT NULL ); CREATE TABLE Employees ( EmpID INT PRIMARY KEY, EmpName NVARCHAR(50), DeptID INT FOREIGN KEY REFERENCES Departments(DeptID) );
核心实现步骤
建立数据库连接
using System.Data.SqlClient; string connectionString = "Server=服务器地址;Database=数据库名;User Id=用户名;Password=密码;"; using (SqlConnection conn = new SqlConnection(connectionString)) { await conn.OpenAsync(); // 异步连接提升性能 }
编写统计SQL语句
string query = @" SELECT d.DeptName AS 部门名称, COUNT(e.EmpID) AS 员工数量 FROM Departments d LEFT JOIN Employees e ON d.DeptID = e.DeptID GROUP BY d.DeptName ORDER BY 员工数量 DESC;";
参数化查询(防范SQL注入):
var command = new SqlCommand(query, conn);
数据读取与处理
using (SqlDataReader reader = await command.ExecuteReaderAsync()) { var result = new List<DepartmentStat>(); while (await reader.ReadAsync()) { result.Add(new DepartmentStat { Department = reader["部门名称"].ToString(), EmployeeCount = Convert.ToInt32(reader["员工数量"]) }); } // 转换为JSON输出示例 return JsonConvert.SerializeObject(result); } // 数据模型类 public class DepartmentStat { public string Department { get; set; } public int EmployeeCount { get; set; } }
异常处理机制
try { // 数据库操作代码 } catch (SqlException ex) { Console.WriteLine($"数据库错误: {ex.Number} - {ex.Message}"); // 记录错误日志 Logger.LogError(ex, "部门统计失败"); } catch (Exception ex) { Console.WriteLine($"系统异常: {ex.Message}"); }
高级优化方案
缓存策略
// 使用MemoryCache减少数据库压力 var stats = MemoryCache.Default.Get("DeptStats") as List<DepartmentStat>; if (stats == null) { stats = await GetDepartmentStatsFromDB(); MemoryCache.Default.Add("DeptStats", stats, DateTimeOffset.Now.AddMinutes(30)); }
分库分表处理
// 使用数据库路由策略 if (DateTime.Now.Year > 2020) { connectionString = GetShardingConnectionString(); }
异步并行查询
var tasks = departments.Select(async dept => { var count = await GetEmployeeCountAsync(dept.Id); return new DepartmentStat { Department = dept.Name, EmployeeCount = count }; }); var results = await Task.WhenAll(tasks);
可视化展示方案
将统计结果通过图表呈现:
// 使用ASP.NET Core Chart控件 @using System.Web.UI.DataVisualization.Charting <chart> <Series> <Series Name="部门人数" ChartType="Column"> @foreach (var item in Model) { <Points> <Point Y="@item.EmployeeCount" /> </Points> } </Series> </Series> <ChartAreas> <ChartArea Name="ChartArea1"></ChartArea> </ChartAreas> </chart>
FAQ
Q:部门层级嵌套如何统计?
A:使用递归CTE查询:
WITH RecursiveCTE AS ( SELECT DeptID, ParentDeptID FROM Departments WHERE ParentDeptID IS NULL UNION ALL SELECT d.DeptID, d.ParentDeptID FROM Departments d INNER JOIN RecursiveCTE r ON d.ParentDeptID = r.DeptID )
Q:如何处理海量数据统计?
A:采用以下方案:
- 建立统计专用索引
CREATE NONCLUSTERED INDEX IX_Employees_DeptID ON Employees (DeptID) INCLUDE (EmpID)
- 使用数据库定时任务预计算
- 启用分页查询
技术引用
- Microsoft ADO.NET文档:https://docs.microsoft.com/zh-cn/dotnet/framework/data/adonet/
- SQL Server性能优化指南:https://learn.microsoft.com/sql/relational-databases/performance/
- OWASP SQL注入防护规范:https://owasp.org/www-community/attacks/SQL_Injection