Young87

SmartCat's Blog

So happy to code my life!

游戏开发交流QQ群号60398951

当前位置:首页 >AI写作

c#题例-2025-07-26 03:51:46

当然可以!以下是一道**专家级别**的 C# 逻辑面试题,考察候选人对 **委托、事件、异步编程、线程安全、闭包捕获、设计模式** 等多个高级特性的理解和综合运用能力:

---

### 🧠 面试题:实现一个线程安全的事件总线(Event Bus)并支持异步订阅

#### 背景:
在现代应用程序中,事件总线(Event Bus)是一种常见的设计模式,用于解耦组件之间的通信。你需要实现一个简单的、线程安全的事件总线,支持事件的发布与订阅,并支持异步订阅方法。

---

### 📌 要求:

1. 实现一个 `IEventBus` 接口,包含以下功能:
- `Subscribe(Func handler)`:订阅一个异步事件处理函数。
- `Unsubscribe(Func handler)`:取消订阅。
- `Publish(T @event)`:发布一个事件,通知所有订阅者(异步执行)。

2. 保证线程安全:
- 多线程调用 `Publish`、`Subscribe`、`Unsubscribe` 时不能出现异常或状态不一致。

3. 支持多个事件类型:
- 不同类型的事件应分别处理,互不干扰。

4. 使用 C# 高级特性:
- 委托、泛型、并发集合、异步/await、闭包等。

---

### 💡 示例用法:

```csharp
var eventBus = new EventBus();

// 订阅一个用户注册事件
eventBus.Subscribe(async e =>
{
await SendEmail(e.Email);
Console.WriteLine($"Sent email to {e.Email}");
});

// 发布事件
eventBus.Publish(new UserRegisteredEvent { Email = "test@example.com" });
```

---

### 🧪 附加问题(用于深入考察):

1. 如何避免内存泄漏?如何管理订阅者的生命周期?
2. 如何处理异常?订阅者的异常是否会影响其他订阅者?
3. 如何支持同步和异步混合的订阅方式?
4. 如何提升性能?比如使用 `ValueTask` 或缓存委托?
5. 如何扩展支持事件过滤(如基于标签或条件)?

---

### ✅ 参考答案(部分实现):

```csharp
public interface IEventBus
{
void Subscribe(Func handler);
void Unsubscribe(Func handler);
void Publish(T @event);
}

public class EventBus : IEventBus
{
private readonly ConcurrentDictionary _handlers =
new ConcurrentDictionary();

public void Subscribe(Func handler)
{
var handlers = GetOrAddHandlerList();
handlers.Add(handler);
}

public void Unsubscribe(Func handler)
{
var type = typeof(T);
if (_handlers.TryGetValue(type, out var list))
{
((List>)list).Remove(handler);
}
}

public void Publish(T @event)
{
var handlers = GetHandlerList();
if (handlers == null) return;

foreach (var handler in handlers.ToList())
{
// Fire and forget
Task.Run(async () => await handler(@event));
}
}

private List> GetOrAddHandlerList()
{
return (List>)_handlers.GetOrAdd(
typeof(T),
_ => new List>());
}

private List> GetHandlerList()
{
_handlers.TryGetValue(typeof(T), out var list);
return (List>)list;
}
}

// 示例事件
public class UserRegisteredEvent
{
public string Email { get; set; }
}
```

---

### 🎯 考察点总结:

| 考察点 | 描述 |
|--------|------|
| 泛型 | 使用泛型支持多种事件类型 |
| 委托 | 使用 `Func` 表示异步事件处理 |
| 线程安全 | 使用 `ConcurrentDictionary` 和线程安全访问 |
| 异步编程 | 使用 `async/await` 和 `Task.Run` |
| 闭包捕获 | 潜在的闭包问题(如捕获事件对象) |
| 设计模式 | 事件总线模式、观察者模式 |
| 性能优化 | 是否考虑并发性能、避免锁 |
| 扩展性 | 是否容易支持过滤、优先级、生命周期管理 |

---

如果你希望我提供一个完整可运行的项目模板或进一步扩展功能(比如支持事件处理器优先级、自动取消订阅等),也可以告诉我!

除特别声明,本站所有文章均为原创,如需转载请以超级链接形式注明出处:SmartCat's Blog

上一篇: c#题例-2025-07-26 09:25:01

下一篇: c#题例-2025-07-25 22:18:36

精华推荐