如何将VB.NET结构数组Persons写入文件并从文件读取?
解决方案
首先需要给Person结构添加可序列化特性,才能通过.NET序列化机制将其写入文件。同时修正原代码中数组索引的小问题(原代码从索引1开始存储,浪费了索引0的位置),再实现保存和读取逻辑并加入异常处理,避免程序冻结。
1. 修改Person结构
给结构添加<Serializable()> 特性,这是序列化的前提:
<Serializable()> Structure Person Public name As String Public height As Integer Public weight As Double End Structure
2. 实现保存功能(saveBtn_Click)
使用BinaryFormatter序列化已添加的有效Person数据到文件,搭配文件选择对话框让用户指定保存路径,同时加入异常处理:
Private Sub saveBtn_Click(sender As Object, e As EventArgs) Handles saveBtn.Click ' 只提取已添加的有效数据,避免序列化空元素 Dim validPersons As Person() = persons.Take(arraySize).ToArray() Using saveDialog As New SaveFileDialog() saveDialog.Filter = "二进制文件 (*.dat)|*.dat|所有文件 (*.*)|*.*" saveDialog.Title = "保存人员数据" If saveDialog.ShowDialog() = DialogResult.OK Then Try Using fs As New FileStream(saveDialog.FileName, FileMode.Create) Dim formatter As New BinaryFormatter() formatter.Serialize(fs, validPersons) End Using MsgBox("数据保存成功!") Catch ex As Exception MsgBox($"保存失败:{ex.Message}") End Try End If End Using End Sub
3. 实现读取功能(readBtn_Click)
从文件反序列化Person数组,更新原有数据容器,同样加入异常处理防止程序崩溃:
Private Sub readBtn_Click(sender As Object, e As EventArgs) Handles readBtn.Click Using openDialog As New OpenFileDialog() openDialog.Filter = "二进制文件 (*.dat)|*.dat|所有文件 (*.*)|*.*" openDialog.Title = "读取人员数据" If openDialog.ShowDialog() = DialogResult.OK Then Try Using fs As New FileStream(openDialog.FileName, FileMode.Open) Dim formatter As New BinaryFormatter() Dim loadedPersons As Person() = DirectCast(formatter.Deserialize(fs), Person()) ' 重置原有数据并加载新数据,确保不超过数组最大容量 arraySize = loadedPersons.Length If arraySize > 50 Then arraySize = 50 End If Array.Copy(loadedPersons, persons, arraySize) End Using MsgBox("数据读取成功!") Catch ex As Exception MsgBox($"读取失败:{ex.Message}") End Try End If End Using End Sub
4. 修正原submitBtn_Click的索引问题
原代码中先自增arraySize再赋值,导致第一个元素存在于persons(1),修正为先赋值再自增,同时添加基础输入验证:
Private Sub submitBtn_Click(sender As Object, e As EventArgs) Handles submitBtn.Click If arraySize < 50 Then Dim Name As String Dim Height As Integer Dim Weight As Double ' 基础输入验证,避免转换错误 If String.IsNullOrEmpty(nameTxt.Text) OrElse Not Integer.TryParse(heightTxt.Text, Height) OrElse Not Double.TryParse(weightTxt.Text, Weight) Then MsgBox("请输入有效的数据!") Return End If nameTxt.Text = Nothing heightTxt.Text = Nothing weightTxt.Text = Nothing ' 先赋值给当前arraySize索引,再自增 persons(arraySize).name = Name persons(arraySize).height = Height persons(arraySize).weight = Weight arraySize += 1 Else MsgBox("人员列表已满,无法添加新数据。") End If End Sub
关键说明
- 必须标记
Person为可序列化,否则无法完成二进制序列化操作。 - 只序列化已添加的有效数据,避免写入大量默认值的空元素。
- 加入
Try-Catch块捕获文件操作异常,防止因错误导致程序冻结。 - 使用文件选择对话框让用户自主选择路径,提升程序灵活性。
内容的提问来源于stack exchange,提问作者George MacLennan
相关产品推荐
相关产品推荐

