# 第八课：异常处理

## 什么是异常

异常 = 程序运行时的错误，导致程序无法正常继续。

```csharp
int[] numbers = { 1, 2, 3 };
int x = numbers[10];  // 索引越界 → 抛出 IndexOutOfRangeException
```

## try / catch / finally

```csharp
try
{
    // 可能出错的代码放这里
    int[] numbers = { 1, 2, 3 };
    int x = numbers[10];
}
catch (Exception ex)
{
    // 捕获异常并处理
    Console.WriteLine($"出错了: {ex.Message}");
}
finally
{
    // 无论是否出错，都会执行（通常放清理代码）
    Console.WriteLine("无论怎样都会执行");
}
```

## 捕获特定异常类型

```csharp
try
{
    int a = int.Parse("abc");  // 格式错误
}
catch (FormatException ex)
{
    Console.WriteLine("格式错误");
}
catch (OverflowException ex)
{
    Console.WriteLine("数字溢出");
}
catch (Exception ex)
{
    Console.WriteLine($"未知错误: {ex.Message}");
}
```

## 常见异常类型

| 异常类型 | 触发场景 |
|----------|----------|
| `FormatException` | 格式错误（`int.Parse("abc")`） |
| `NullReferenceException` | 空对象访问（`obj.Method()`，`obj` 为 null） |
| `IndexOutOfRangeException` | 数组越界 |
| `FileNotFoundException` | 文件不存在 |
| `DivideByZeroException` | 除数为零 |
| `InvalidOperationException` | 操作无效状态 |

## throw 抛出异常

```csharp
static void SetAge(int age)
{
    if (age < 0 || age > 150)
    {
        throw new ArgumentException("年龄必须在 0-150 之间");
    }
    Console.WriteLine($"年龄设置为: {age}");
}
```

```csharp
try
{
    SetAge(-5);
}
catch (ArgumentException ex)
{
    Console.WriteLine($"参数错误: {ex.Message}");
}
```

## 自定义异常

```csharp
class MicrophoneException : Exception
{
    public MicrophoneException(string message) : base(message) { }
    public MicrophoneException(string message, Exception inner) : base(message, inner) { }
}
```

## finally 的作用

```csharp
FileStream file = null;
try
{
    file = new FileStream("test.txt", FileMode.Open);
    // 读取文件...
}
catch (FileNotFoundException ex)
{
    Console.WriteLine("文件不存在");
}
finally
{
    // 确保文件被关闭
    file?.Close();
}
```

## using 语句（更简洁）

```csharp
// using 自动释放资源（相当于 try-finally）
using (FileStream file = new FileStream("test.txt", FileMode.Open))
{
    // 使用 file
}  // 作用域结束后自动 Close()
```

## 实际项目应用

```csharp
try
{
    // 尝试连接麦克风
    microphone.Connect();
}
catch (DeviceNotFoundException ex)
{
    Console.WriteLine("麦克风未找到，请检查连接");
    ShowReconnectDialog();
}
catch (UnauthorizedAccessException ex)
{
    Console.WriteLine("没有权限访问麦克风");
    RequestPermission();
}
catch (Exception ex)
{
    Console.WriteLine($"未知错误: {ex.Message}");
    LogError(ex);
}
```

## 不要过度捕获异常

```csharp
// ✗ 不好：捕获所有异常但不处理
try { DoSomething(); }
catch { }

// ✓ 好：只捕获能处理的异常
try { Connect(); }
catch (DeviceNotFoundException ex) { ShowError(); }
```
