C# 10 引入了 global using 指令,旨在简化代码,减少重复的 using 声明。它可以在项目级别定义全局生效的 using 语句,无需在每个代码文件中重复声明。
1. 什么是 global using?
global using 是 C# 10 的一个特性,通过在 using 关键字前加上 global 关键字,使该命名空间在整个项目中全局生效。这样,项目内所有代码文件都能自动引用该命名空间,无需手动添加 using 指令。
示例:
csharp
// 在任意 .cs 文件中使用
global using System.Text.Json;
声明后,项目中所有文件都可以直接使用 JsonSerializer 等类型,而不需要再写 using System.Text.Json;。
2. 如何使用 global using?
基本用法
- 语法:
global using <命名空间>; - 必须放在任何代码文件的顶部,不能 放在
namespace声明内部。 - 可以出现在任何 .cs 文件中,但推荐统一管理。
推荐实践:使用 GlobalUsings.cs 文件
在项目中创建一个名为 GlobalUsings.cs 的专用文件,将所有全局 using 集中管理。这是目前社区和微软推荐的最佳实践。
示例:
csharp
// GlobalUsings.cs
global using System;
global using System.Collections.Generic;
global using System.Linq;
global using System.Threading.Tasks;
global using Microsoft.EntityFrameworkCore;
默认的全局引用
当创建 .NET 6+ 新项目(如控制台、Web API 等)时,SDK 会隐式生成 常用命名空间的全局引用。这反映在项目文件中的 ImplicitUsings 设置:
xml
<PropertyGroup>
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>
启用后,以下命名空间会自动全局可用的(以控制台程序为例):
SystemSystem.Collections.GenericSystem.IOSystem.LinqSystem.Net.HttpSystem.ThreadingSystem.Threading.Tasks
3. global using 的注意事项
不能放在 namespace 内部
csharp
namespace MyApp
{
global using System; // ❌ 编译错误
}
条件编译支持
global using 可以与条件编译结合:
csharp
#if DEBUG
global using System.Diagnostics;
#endif
显式与隐式的关系
- 隐式全局引用(由 SDK 自动生成)的命名空间可以删除。
- 显式全局引用 (手动写的
global using)也可以通过显式声明来隐藏或覆盖。
多个文件中使用
global using 可以在多个文件中声明,但如果同一命名空间出现两次,会触发 CS8801 警告。确保同一命名空间只被声明一次。
4. 常见场景
| 场景 | 示例 |
|---|---|
| 基础库 | global using System.Text.Json; |
| EF Core | global using Microsoft.EntityFrameworkCore; |
| 日志 | global using Microsoft.Extensions.Logging; |
| 依赖注入 | global using Microsoft.Extensions.DependencyInjection; |
| 自定义项目命名空间 | global using MyApp.Common; |
5. 总结
global using 的优势:
- 减少重复代码,提升开发效率
- 统一管理项目引用,降低维护成本
- 与新项目模板的
ImplicitUsings配合使用效果更佳
适用建议:
- 基础、稳定且项目全局使用的命名空间适合作为
global using(如System、System.Linq等) - 特定于某个模块的命名空间仍建议使用传统
using,保持模块独立性