TE
科技回声
首页24小时热榜最新最佳问答展示工作
GitHubTwitter
首页

科技回声

基于 Next.js 构建的科技新闻平台,提供全球科技新闻和讨论内容。

GitHubTwitter

首页

首页最新最佳问答展示工作

资源链接

HackerNews API原版 HackerNewsNext.js

© 2025 科技回声. 版权所有。

Serialization for C# Games

133 点作者 jolexxa11 个月前

10 条评论

flohofwoe11 个月前
If I learned one important lesson from writing savegame systems: don&#x27;t directly serialize your entire game state on the &quot;game object level&quot; (e.g. don&#x27;t create a savegame by running a serializer over your game object soup), instead decouple the saved data from your game logic internals, have a clear boundary between your game logic and the savegame-system, keep the saved state as minimal as possible, and reconstruct or default-initialize the rest of the data after loading saved state.<p>With that approach, a language-assisted serialization system also looses a lot of its appeal IMHO (although it can still be useful of course for describing the separate savegame data format).<p>Also: resist the architecture astronaut in you, especially savegame systems are a honey trap for overengineering ;)
评论 #40728679 未加载
评论 #40730436 未加载
评论 #40725867 未加载
LeonB11 个月前
In my personal projects I’ve been using variations on the same simple code for saving&#x2F;loadings objects for a decade or so, and have very few problems. The heart of the code is this interface -<p><pre><code> public interface IStashy&lt;K&gt; { void Save&lt;T&gt;(T t, K id); T Load&lt;T&gt;(K id); IEnumerable&lt;T&gt; LoadAll&lt;T&gt;(); void Delete&lt;T&gt;(K id); K GetNewId&lt;T&gt;(); } </code></pre> And implementations of that are very stable over time. Objects get serialized as json and stored in a folder named after their type.<p>There’s a small number of gotchas, for which I have well known work arounds:<p>- I generally won’t remove a property, but mark it as obsolete and stop using it.<p>- If I’ve added a new Boolean property, I’d tend to name it such that it defaults to false, or if it must default to true, have it stored in a nullable boolean, and if it loads as null (from an older instance of the type), set it to the default.<p>- some convenient types I want to use (as properties) are not serializable, so before saving I’ll copy their data into a serializable type, like an array of key values, then on loading rehydrate that to a dictionary. (I guess this is a harsh performance penalty if you’re doing a lot of it in a game)
评论 #40724689 未加载
评论 #40725405 未加载
评论 #40723948 未加载
interroboink11 个月前
Sometimes, when battling these issues, I wish the Smalltalk-style approach[1][2] was more popular&#x2F;feasible. Basically, saving the entire state of the VM is a fundamental operation supported by the language. Only truly transient things like network connections require special effort.<p>There are some echoes of this with things like Lua&#x27;s Pluto&#x2F;Eris, or serializable continuations in other languages (eg: Perl&#x27;s Continuity).<p>It&#x27;s just such a pain to <i>thoroughly</i> handle that sort of stuff without language-level support. And doing a &quot;good enough&quot; approach with some rough edges is usually shippable, so it&#x27;s hard to build a critical mass of demand for such support. And even if there was, it&#x27;s very hard to add it to a language&#x2F;framework&#x2F;etc that wasn&#x27;t designed for it to begin with.<p>I&#x27;ve had a decent experience with &#x27;struct string&#x27; style approaches, like Lua&#x27;s string.pack() or Perl&#x27;s pack()[3]. It&#x27;s a little brittle, but extremely straightforward and &quot;not framework-y,&quot; which suits me. But it leaves out things like program execution state; it&#x27;s just for plain data.<p>[1] <a href="https:&#x2F;&#x2F;en.wikipedia.org&#x2F;wiki&#x2F;Smalltalk#Image-based_persistence" rel="nofollow">https:&#x2F;&#x2F;en.wikipedia.org&#x2F;wiki&#x2F;Smalltalk#Image-based_persiste...</a><p>[2] example of using this serializable statefulness for serving web apps: <a href="https:&#x2F;&#x2F;en.wikipedia.org&#x2F;wiki&#x2F;Seaside_(software)" rel="nofollow">https:&#x2F;&#x2F;en.wikipedia.org&#x2F;wiki&#x2F;Seaside_(software)</a><p>[3] <a href="https:&#x2F;&#x2F;perldoc.perl.org&#x2F;functions&#x2F;pack" rel="nofollow">https:&#x2F;&#x2F;perldoc.perl.org&#x2F;functions&#x2F;pack</a>
评论 #40725146 未加载
评论 #40730297 未加载
评论 #40724900 未加载
kogir11 个月前
This seems to cover many common pain points, but I’ve written my fair share of .NET serializers and for anything I build now I’d just use protocol buffers. Robust support, handles versioning pretty well, and works cross platform.<p>I’d like to know their reasons for making yet another serializer vs just using pb or thrift.
评论 #40730147 未加载
wheybags11 个月前
In my experience, the pain of dealing with changes outweighs the pain of dealing with boilerplate, so it&#x27;s better to explicitly write out save and load functions manually than rely on reflection.<p>Also means you can do stuff like if(version&lt;x) { load old thing + migrate} else {load new thing} very easily. And it&#x27;s just code, not magic.
评论 #40730056 未加载
评论 #40729171 未加载
jayd1611 个月前
I want to like this because it seems well done but I kind of grimace instead. It&#x27;s not the library&#x27;s fault.<p>Game engines have some form of serialization already (most of what a game engine does is load a serialized game state into memory, imo).<p>I&#x27;ve found its usually better to try to leverage those systems so you&#x27;re not building multiple models objects and doing conversions between game engine and serialized types.<p>Engines often do a lot of (design)work to load things directly into memory in such a way that the game engine can use the inflated object immediately without a lot of parsing. It&#x27;s nice to try to leverage that. Moreover less plugins is less complexity in the build process etc etc.<p>Those desires give me pause when looking at serialization plugins in the context of game engines.<p>Howeve, it&#x27;s also not entirely feasible to only use the core engine systems in all cases. Often what&#x27;s available at runtime for a game engine isn&#x27;t always the same as build time. You might need to read this data outside of the engine and then you&#x27;re really out of luck...life&#x27;s so complicated.
Madmallard11 个月前
RunUO has an implementation of this and it&#x27;s like 25 years old but still worked really well
评论 #40730255 未加载
评论 #40723823 未加载
评论 #40724550 未加载
isthiseasymode11 个月前
Naive question: is there a reason why SQLite wouldn’t work for something like this?
评论 #40724018 未加载
评论 #40725627 未加载
评论 #40724624 未加载
评论 #40723972 未加载
评论 #40729217 未加载
评论 #40725031 未加载
评论 #40727326 未加载
penetrarthur11 个月前
There&#x27;s a very good MessagePack serialization library for C#. I&#x27;ve used it in many of the games I worked on.<p><a href="https:&#x2F;&#x2F;github.com&#x2F;MessagePack-CSharp&#x2F;MessagePack-CSharp">https:&#x2F;&#x2F;github.com&#x2F;MessagePack-CSharp&#x2F;MessagePack-CSharp</a>
scotty7911 个月前
How this subject is approached in ECS? Just add Save component that knows how to serialize to all objects that need to be saved and a system that dumps alive objects into a file?