WinForm 学习总结 - 第二十六天(文件操作与数据存取)


一、文件操作概述

1.1 数据存储方式对比

存储方式 适用场景 特点
数据库存取 大量、关系复杂的数据 支持复杂查询、事务处理
文件存取 少量、数据关系简单 读取方便、可存储在任何介质

1.2 System.IO 命名空间核心类

类名 说明
BinaryReader 从二进制流读取原始数据
BinaryWriter 以二进制格式写入原始数据
BufferedStream 字节流的临时存储(缓冲区)
Directory 操作目录结构
DirectoryInfo 对目录执行操作
DriveInfo 提供驱动器信息
File 处理文件(静态方法)
FileInfo 对文件执行操作(实例方法)
FileStream 文件中任意位置的读写
MemoryStream 随机访问内存中的数据流
Path 对路径信息执行操作
StreamReader 从字节流中读取字符
StreamWriter 向流中写入字符

二、FileStream 类(文件流)

2.1 FileStream 构造函数

FileStream <object_name> = new FileStream(
    <file_name>,      // 文件路径
    <FileMode>,        // 文件操作模式
    <FileAccess>,      // 文件访问权限
    <FileShare>         // 文件共享模式
);

2.2 FileMode 枚举(文件操作模式)

成员 说明
Create 创建新文件,如果存在则覆盖
Open 打开已有文件,不存在则抛异常
OpenOrCreate 打开已有文件,不存在则创建
Append 打开文件并在末尾追加
Truncate 打开文件并清空内容
CreateNew 创建新文件,存在则抛异常

2.3 FileAccess 枚举(访问权限)

成员 说明
Read 只读权限
Write 只写权限
ReadWrite 读写权限

2.4 FileStream 读取文件

// 1. 创建 FileStream 对象
FileStream fileStream = new FileStream(
    @"1.txt",                      // 文件路径
    FileMode.Open,                 // 打开模式
    FileAccess.Read                // 只读权限
);

// 2. 创建字节数组缓冲区(5MB)
byte[] buffer = new byte[1024 * 1024 * 5];

// 3. 读取数据到缓冲区
int length = fileStream.Read(buffer, 0, buffer.Length);

// 4. 将字节数组转换为字符串
string info = Encoding.Default.GetString(buffer, 0, length);

// 5. 显示到 WinForm 控件
label1.Text = info;

// 6. 关闭流并释放资源
fileStream.Close();
fileStream.Dispose();

2.5 FileStream 写入文件

// 1. 创建文件流(覆盖模式)
FileStream file = new FileStream(
    @"1.txt",
    FileMode.Create,    // 如果存在则覆盖
    FileAccess.Write    // 写权限
);

// 2. 要写入的字符串
string info = "写入的内容";

// 3. 字符串转字节数组
byte[] bs = Encoding.Default.GetBytes(info);

// 4. 写入数据
file.Write(bs, 0, bs.Length);

// 5. 关闭并释放
file.Close();
file.Dispose();

2.6 WinForm 中读取文件示例

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
    }

    private void button1_Click(object sender, EventArgs e)
    {
        // 使用 FileStream 读取文件
        FileStream fileStream = new FileStream(@"1.txt", FileMode.Open, FileAccess.Read);
        
        // 创建缓冲区
        byte[] buffer = new byte[1024 * 1024 * 5];
        
        // 读取文件内容
        int length = fileStream.Read(buffer, 0, buffer.Length);
        
        // 字节数组转字符串
        string info = Encoding.Default.GetString(buffer, 0, length);
        
        // 显示到标签
        label1.Text = info;
        
        // 关闭流
        fileStream.Close();
        fileStream.Dispose();
    }
}

三、using 语句与资源管理

3.1 using 语句的优势

using 语句会自动在作用域结束时调用 Dispose() 方法,简化资源管理,无需手动调用 Close()Dispose()

3.2 using 语句写入文件

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        string s = "要写入的内容";
        byte[] bs = Encoding.Default.GetBytes(s);

        // 使用 using 自动管理资源
        using (FileStream fs = new FileStream(@"1.txt", FileMode.Append))
        {
            fs.Write(bs, 0, bs.Length);
        }
        // 在此处 fs 已被自动释放
    }
}

3.3 using 语句读取文件

private void ReadFileButton_Click(object sender, EventArgs e)
{
    byte[] buffer = new byte[1024 * 1024 * 5];
    
    using (FileStream fs = new FileStream(@"1.txt", FileMode.Open))
    {
        int length = fs.Read(buffer, 0, buffer.Length);
        string content = Encoding.Default.GetString(buffer, 0, length);
        
        MessageBox.Show(content);
    }
    // fs 自动关闭和释放
}

四、Directory 类(目录操作)

4.1 创建目录

// 创建单层目录
Directory.CreateDirectory(@"C:\Users\Administrator\Desktop\FirstDay");

// 创建多层目录(会自动创建中间目录)
Directory.CreateDirectory(@"C:\Test\SubFolder\DeepFolder");

4.2 获取目录内容

// 获取目录下的所有文件和子目录名称
string[] paths = Directory.GetFileSystemEntries(@"C:\Users\Administrator\Desktop\本天知识");

// 获取目录下的所有子目录
string[] directories = Directory.GetDirectories(@"C:\Users\Administrator\Desktop\本天知识");

// 获取目录下的所有文件
string[] files = Directory.GetFiles(@"C:\Users\Administrator\Desktop\本天知识");

4.3 删除目录

// 删除空目录
Directory.Delete(@"C:\Users\Administrator\Desktop\FirstDay\新建文件夹");

// 删除非空目录(递归删除所有子文件和子目录)
new DirectoryInfo(@"C:\Users\Administrator\Desktop\FirstDay\新建文件夹").Delete(true);

4.4 递归遍历目录结构

/// <summary>
/// 使用递归遍历文件夹下所有文件和子目录
/// </summary>
/// <param name="path">要遍历的目录路径</param>
/// <param name="count">缩进级别</param>
void 递归遍历文件夹(string path, int count = 0)
{
    // 判断路径是否存在
    if (!Directory.Exists(path)) return;

    // 生成缩进字符串
    string indent = new string(' ', count);

    // 获取并打印文件
    foreach (var item in Directory.GetFiles(path))
    {
        Console.WriteLine($"{indent}文件: {Path.GetFileName(item)}");
    }

    // 遍历子目录
    foreach (var item in Directory.GetDirectories(path))
    {
        Console.WriteLine($"{indent}文件夹: {Path.GetFileName(item)}");
        
        // 递归调用,深度加2
        递归遍历文件夹(item, count + 2);
    }
}

// 调用示例
递归遍历文件夹(@"C:\Users\Administrator\Desktop\本天知识");

五、File 类(静态文件操作)

5.1 常用静态方法

方法 说明
Create() 创建或覆盖文件
Delete() 删除文件
Move() 移动文件(相当于剪切)
Copy() 复制文件
Exists() 判断文件是否存在

5.2 文件内容操作方法

方法 数据类型 说明
WriteAllBytes() / ReadAllBytes() 字节数组 整体读写
WriteAllLines() / ReadAllLines() 字符串数组 按行读写
WriteAllText() / ReadAllText() 字符串 整体读写
AppendAllText() 字符串 追加写入

5.3 File 类的便捷方法

// 写入字节数组
File.WriteAllBytes("123.txt", Encoding.UTF8.GetBytes("内容"));

// 读取字节数组
byte[] data = File.ReadAllBytes("123.txt");

// 写入字符串数组(每行一个元素)
string[] lines = { "第一行", "第二行", "第三行" };
File.WriteAllLines("123.txt", lines);

// 读取字符串数组
string[] lines = File.ReadAllLines("123.txt");

// 写入字符串
File.WriteAllText("123.txt", "这是一段文本内容");

// 读取字符串
string content = File.ReadAllText("123.txt");

// 追加内容
File.AppendAllText("123.txt", "追加的内容");

六、StreamReader 和 StreamWriter(文本流)

6.1 StreamWriter 写入文本

// 创建流写入器
StreamWriter sw = new StreamWriter("1.txt");

string[] names = { "吴亦凡", "李云迪", "蔡徐坤" };

foreach (string name in names)
{
    sw.WriteLine(name);  // 写入一行
}

sw.Close();

6.2 StreamReader 读取文本

// 创建流读取器
StreamReader sr = new StreamReader("1.txt");

string line;
while ((line = sr.ReadLine()) != null)  // 逐行读取
{
    Console.WriteLine(line);
}

sr.Close();

6.3 WinForm 中使用 StreamReader

private void LoadTextButton_Click(object sender, EventArgs e)
{
    using (StreamReader sr = new StreamReader(@"log.txt", Encoding.UTF8))
    {
        textBox1.Text = sr.ReadToEnd();  // 读取全部内容
    }
}

private void SaveTextButton_Click(object sender, EventArgs e)
{
    using (StreamWriter sw = new StreamWriter(@"log.txt", false, Encoding.UTF8))
    {
        sw.Write(textBox1.Text);  // 写入全部内容
    }
    MessageBox.Show("保存成功!");
}

七、Path 类(路径操作)

7.1 常用静态方法

方法 说明
GetFileName() 获取文件名(含扩展名)
GetFileNameWithoutExtension() 获取文件名(不含扩展名)
GetExtension() 获取文件扩展名
GetDirectoryName() 获取目录路径
Combine() 合并路径
ChangeExtension() 更改扩展名

7.2 Path 类使用示例

string fullPath = @"C:\TestFolder\myfile.txt";

// 获取文件名
string fileName = Path.GetFileName(fullPath);        // "myfile.txt"

// 获取不含扩展名的文件名
string nameWithoutExt = Path.GetFileNameWithoutExtension(fullPath);  // "myfile"

// 获取扩展名
string extension = Path.GetExtension(fullPath);        // ".txt"

// 获取目录路径
string directory = Path.GetDirectoryName(fullPath);   // "C:\TestFolder"

// 合并路径
string combined = Path.Combine(@"C:\Test\", "file.txt");  // "C:\Test\file.txt"

// 更改扩展名
string newPath = Path.ChangeExtension(fullPath, ".doc");  // "C:\TestFolder\myfile.doc"

八、DriveInfo 类(驱动器信息)

8.1 主要属性

属性 说明
Name 驱动器名称(如 “C:”)
DriveType 驱动器类型(固定、可移动、网络等)
DriveFormat 文件系统格式(如 “NTFS”、“FAT32”)
IsReady 驱动器是否就绪
TotalSize 总存储空间(字节)
TotalFreeSpace 可用空间(字节)
AvailableFreeSpace 当前用户可用空间(字节)
VolumeLabel 卷标名称

8.2 获取驱动器信息

// 获取 C 盘信息
DriveInfo driveInfo = new DriveInfo(@"C:\");

Console.WriteLine($"驱动器: {driveInfo.Name}");
Console.WriteLine($"类型: {driveInfo.DriveType}");
Console.WriteLine($"文件系统: {driveInfo.DriveFormat}");
Console.WriteLine($"是否就绪: {driveInfo.IsReady}");
Console.WriteLine($"总大小: {driveInfo.TotalSize / 1024.0 / 1024 / 1024:F2} GB");
Console.WriteLine($"可用空间: {driveInfo.AvailableFreeSpace / 1024.0 / 1024 / 1024:F2} GB");

// 获取所有驱动器
DriveInfo[] allDrives = DriveInfo.GetDrives();
foreach (DriveInfo drive in allDrives)
{
    if (drive.IsReady)
    {
        Console.WriteLine($"驱动器 {drive.Name}: {drive.TotalFreeSpace / 1024.0 / 1024 / 1024:F2} GB 可用");
    }
}

九、Environment 类(环境信息)

9.1 常用属性

属性 说明
CurrentDirectory 当前工作目录
MachineName 计算机名称
UserName 当前用户名
OSVersion 操作系统版本
SystemDirectory 系统目录路径
TickCount 系统启动后的毫秒数
NewLine 换行符

9.2 常用方法

方法 说明
GetLogicalDrives() 获取所有逻辑驱动器
GetFolderPath() 获取特殊文件夹路径
Exit() 退出进程

9.3 Environment 使用示例

// 获取当前工作目录
string currentDir = Environment.CurrentDirectory;

// 获取计算机名
string machineName = Environment.MachineName;

// 获取用户名
string userName = Environment.UserName;

// 获取系统目录
string systemDir = Environment.SystemDirectory;

// 获取特殊文件夹路径
string desktopPath = Environment.GetFolderPath(Environment.SpecialFolder.Desktop);
string myDocPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);

// 获取所有逻辑驱动器
string[] drives = Environment.GetLogicalDrives();

// 退出程序
Environment.Exit(0);

十、文件属性操作

10.1 FileInfo 类使用

FileInfo fileInfo = new FileInfo(@"C:\Test\123.txt");

// 获取文件属性
Console.WriteLine($"文件名: {fileInfo.Name}");
Console.WriteLine($"完整路径: {fileInfo.FullName}");
Console.WriteLine($"扩展名: {fileInfo.Extension}");
Console.WriteLine($"大小: {fileInfo.Length} 字节");
Console.WriteLine($"创建时间: {fileInfo.CreationTime}");
Console.WriteLine($"修改时间: {fileInfo.LastWriteTime}");
Console.WriteLine($"访问时间: {fileInfo.LastAccessTime}");
Console.WriteLine($"是否存在: {fileInfo.Exists}");
Console.WriteLine($"是否只读: {fileInfo.IsReadOnly}");

10.2 设置文件属性

FileInfo fileInfo = new FileInfo(@"C:\Test\123.txt");

// 设置单个属性
fileInfo.Attributes = FileAttributes.ReadOnly;   // 只读
fileInfo.Attributes = FileAttributes.Hidden;     // 隐藏

// 同时设置多个属性
fileInfo.Attributes = FileAttributes.Hidden | FileAttributes.ReadOnly;

// 使用 File 类设置属性
File.SetAttributes(@"C:\Test\456.txt", FileAttributes.Hidden);
File.SetAttributes(@"C:\Test\456.txt", FileAttributes.ReadOnly | FileAttributes.Hidden);

十二、最佳实践

12.1 资源管理

  1. 始终使用 using 语句

    // ✅ 正确
    using (FileStream fs = new FileStream("file.txt", FileMode.Open))
    {
        // 操作文件
    }
    
    // ❌ 错误
    FileStream fs = new FileStream("file.txt", FileMode.Open);
    // 可能忘记关闭
    
  2. 手动管理时的正确顺序

    FileStream fs = null;
    try
    {
        fs = new FileStream("file.txt", FileMode.Open);
        // 操作文件
    }
    finally
    {
        if (fs != null)
        {
            fs.Close();
            fs.Dispose();
        }
    }
    

12.2 路径处理

  1. 使用 @ 前缀处理反斜杠

    // ✅ 推荐
    string path = @"C:\Test\file.txt";
    
    // ❌ 不推荐
    string path = "C:\\Test\\file.txt";
    
  2. 使用 Path.Combine 合并路径

    string path = Path.Combine(folderPath, fileName);
    

12.3 编码处理

  1. 统一使用 UTF8 编码

    Encoding.UTF8.GetBytes("内容");
    Encoding.UTF8.GetString(buffer);
    
  2. 根据文件内容选择编码

    // 中文Windows默认使用Default编码
    Encoding.Default.GetBytes("内容");
    

12.4 异常处理

try
{
    FileStream fs = new FileStream("file.txt", FileMode.Open);
    // 操作文件
}
catch (FileNotFoundException)
{
    MessageBox.Show("文件不存在!");
}
catch (IOException)
{
    MessageBox.Show("文件读取错误!");
}
finally
{
    // 清理资源
}

更多推荐