Unity - 向二进制格式的保存数据添加新变量?
Unity - Adding new variables to binary formatted save data?
我使用二进制格式化程序来保存用户数据,其中包括一堆嵌套的 classes 和参数。当我需要向任何 class 添加新参数时,对于来自以前版本的用户,游戏会加载损坏的 data/no 数据。
我尝试在加载后对新变量进行 null 检查,如果它为 null 但它不是修复,则从默认数据复制。游戏没有崩溃,但用户数据中的所有价格和等级都丢失了。
public void Load()
{
GameData = new GameDataModel();
if (File.Exists(GameFilePath + "/" + GameFileName))
{
var bf = new BinaryFormatter();
var file = File.Open(GameFilePath + "/" + GameFileName, FileMode.Open);
var gameData = (GameDataModel)bf.Deserialize(file);
file.Close();
if (string.IsNullOrEmpty(gameData.WorldName))
{
GameData = CreateDefaultGameData();
}
else
{
GameData = gameData;
}
}
else
{
GameData = CreateDefaultGameData();
}
for (int i = 0; i < GameData.Cities.Count; i++)
{
if (GameData.Cities[i].FoodStall == null)
GameData.Cities[i].FoodStall = CreateDefaultGameData().Cities[i].FoodStall;
if (GameData.Cities[i].Billboard == null)
GameData.Cities[i].Billboard = CreateDefaultGameData().Cities[i].Billboard;
if (GameData.Cities[i].Trees == null)
GameData.Cities[i].Trees = CreateDefaultGameData().Cities[i].Trees;
if (GameData.Cities[i].Decorations == null)
GameData.Cities[i].Decorations = CreateDefaultGameData().Cities[i].Decorations;
if (GameData.Cities[i].Station.StationBuildingTypeCosts == null)
GameData.Cities[i].Station.StationBuildingTypeCosts = CreateDefaultGameData().Cities[i].Station.StationBuildingTypeCosts;
if (GameData.Cities[i].Station.StationBuildingType == 0)
GameData.Cities[i].Station.StationBuildingTypeCosts = CreateDefaultGameData().Cities[i].Station.StationBuildingTypeCosts;
if (GameData.Cities[i].Station.CapacityMultiplier == 0)
GameData.Cities[i].Station.CapacityMultiplier = 1;
if (GameData.Cities[i].People.DensityMultiplier == 0)
GameData.Cities[i].People.DensityMultiplier = 1;
if (GameData.Cities[i].Bus.ProfitMultiplier == 0)
GameData.Cities[i].Bus.ProfitMultiplier = 1;
GameData.Cities[i].Station.Parameters = DefaultGameData.Cities[i].Station.Parameters;
GameData.Cities[i].Bus.Parameters = DefaultGameData.Cities[i].Bus.Parameters;
GameData.Cities[i].People.Parameters = DefaultGameData.Cities[i].People.Parameters;
}
}
我希望以前版本的用户保留他们的数据,并有新变量的默认数据。您将如何处理向现有序列化数据添加新数据?
使用保存格式值
通过了解您的保存文件版本,您可以轻松确定是否尝试解码给定值。
如果您没有,请添加一个。否则你将不得不这样做:
public static void deserialize(ref SerializationInfo info, ref StreamingContext context) {
SerializationInfoEnumerator infoEnum = info.GetEnumerator();
Hashtable values = new Hashtable();
while(infoEnum.MoveNext()) {
SerializationEntry val = infoEnum.Current;
values.Add(val.Name, val.Value);
}
...
}
然后使用哈希表来确定给定值是否存在。
如果您使用保存版本,您可以先将其读出,然后查询它以查看会发生什么:从二进制数据中读取值或将其设置为默认值。即 way, way easier.
我使用二进制格式化程序来保存用户数据,其中包括一堆嵌套的 classes 和参数。当我需要向任何 class 添加新参数时,对于来自以前版本的用户,游戏会加载损坏的 data/no 数据。
我尝试在加载后对新变量进行 null 检查,如果它为 null 但它不是修复,则从默认数据复制。游戏没有崩溃,但用户数据中的所有价格和等级都丢失了。
public void Load()
{
GameData = new GameDataModel();
if (File.Exists(GameFilePath + "/" + GameFileName))
{
var bf = new BinaryFormatter();
var file = File.Open(GameFilePath + "/" + GameFileName, FileMode.Open);
var gameData = (GameDataModel)bf.Deserialize(file);
file.Close();
if (string.IsNullOrEmpty(gameData.WorldName))
{
GameData = CreateDefaultGameData();
}
else
{
GameData = gameData;
}
}
else
{
GameData = CreateDefaultGameData();
}
for (int i = 0; i < GameData.Cities.Count; i++)
{
if (GameData.Cities[i].FoodStall == null)
GameData.Cities[i].FoodStall = CreateDefaultGameData().Cities[i].FoodStall;
if (GameData.Cities[i].Billboard == null)
GameData.Cities[i].Billboard = CreateDefaultGameData().Cities[i].Billboard;
if (GameData.Cities[i].Trees == null)
GameData.Cities[i].Trees = CreateDefaultGameData().Cities[i].Trees;
if (GameData.Cities[i].Decorations == null)
GameData.Cities[i].Decorations = CreateDefaultGameData().Cities[i].Decorations;
if (GameData.Cities[i].Station.StationBuildingTypeCosts == null)
GameData.Cities[i].Station.StationBuildingTypeCosts = CreateDefaultGameData().Cities[i].Station.StationBuildingTypeCosts;
if (GameData.Cities[i].Station.StationBuildingType == 0)
GameData.Cities[i].Station.StationBuildingTypeCosts = CreateDefaultGameData().Cities[i].Station.StationBuildingTypeCosts;
if (GameData.Cities[i].Station.CapacityMultiplier == 0)
GameData.Cities[i].Station.CapacityMultiplier = 1;
if (GameData.Cities[i].People.DensityMultiplier == 0)
GameData.Cities[i].People.DensityMultiplier = 1;
if (GameData.Cities[i].Bus.ProfitMultiplier == 0)
GameData.Cities[i].Bus.ProfitMultiplier = 1;
GameData.Cities[i].Station.Parameters = DefaultGameData.Cities[i].Station.Parameters;
GameData.Cities[i].Bus.Parameters = DefaultGameData.Cities[i].Bus.Parameters;
GameData.Cities[i].People.Parameters = DefaultGameData.Cities[i].People.Parameters;
}
}
我希望以前版本的用户保留他们的数据,并有新变量的默认数据。您将如何处理向现有序列化数据添加新数据?
使用保存格式值
通过了解您的保存文件版本,您可以轻松确定是否尝试解码给定值。
如果您没有,请添加一个。否则你将不得不这样做:
public static void deserialize(ref SerializationInfo info, ref StreamingContext context) {
SerializationInfoEnumerator infoEnum = info.GetEnumerator();
Hashtable values = new Hashtable();
while(infoEnum.MoveNext()) {
SerializationEntry val = infoEnum.Current;
values.Add(val.Name, val.Value);
}
...
}
然后使用哈希表来确定给定值是否存在。
如果您使用保存版本,您可以先将其读出,然后查询它以查看会发生什么:从二进制数据中读取值或将其设置为默认值。即 way, way easier.