C# 序列化与数据库
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/765090/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Serializing vs Database
提问by Adi Barda
I believe that the best way to save your application state is to a traditional relational database which most of the time its table structure is pretty much represent the data model of our system + meta data.
我相信保存应用程序状态的最佳方法是使用传统的关系数据库,它的表结构在大多数情况下几乎代表了我们系统的数据模型 + 元数据。
However other guys in my team think that today it's best to simply serialize the entire object graph to a binary or XML file.
No need to say (but I'll still say it) that World War 3 is going between us and I would like to hear your opinion about this issue.
然而,我团队中的其他人认为,今天最好将整个对象图简单地序列化为二进制文件或 XML 文件。
无需说(但我仍然会说)我们之间正在发生第三次世界大战,我想听听您对这个问题的看法。
Personally I hate serialization because:
我个人讨厌序列化,因为:
- The data saved is adhered only to your development platform (C# in my case). No other platforms like Java or C++ can use this data.
- Entire object graph (including all the inheritance chain) is saved and not only the data we need.
- Changing the data model might cause severe backward compatibility issues when trying to load old states.
- Sharing parts of the data between applications is problematic.
- 保存的数据仅适用于您的开发平台(在我的情况下为 C#)。没有其他平台如 Java 或 C++ 可以使用这些数据。
- 保存了整个对象图(包括所有的继承链),而不仅仅是我们需要的数据。
- 尝试加载旧状态时,更改数据模型可能会导致严重的向后兼容性问题。
- 在应用程序之间共享部分数据是有问题的。
I would like to hear your opinion about that.
我想听听你对此的看法。
回答by ConcernedOfTunbridgeWells
See this Stackoverflow postingfor a commentary on the applicability of XML vs. the applicability of a database management system. It discusses an issue that's quite similar to the subject of the debate in your team.
有关XML 的适用性与数据库管理系统的适用性的评论,请参阅此 Stackoverflow 帖子。它讨论的问题与您团队中辩论的主题非常相似。
回答by Chris Morley
You have some good points. I pretty much agree with you, but I'll play the devil's advocate.
你有一些优点。我非常同意你的看法,但我会扮演魔鬼的拥护者。
Well, you could always write a converter in C# to extract the data later if needed.
That's a weak point, because disk space is cheap and the amount of extra bytes we'll use costs far less than the time we'll waste trying to get this all to work your way.
That's the way of the world. Burn the bridges and require upgrades. Convert the data, or make a tool to do that, and then no longer support the old version's way of doing it.
Not if the C# program hands off the data to the other applications. Other applications should not be accessing the data that belongs to this application directly, should they?
好吧,如果需要,您始终可以在 C# 中编写一个转换器以在以后提取数据。
这是一个弱点,因为磁盘空间很便宜,而且我们将使用的额外字节量的成本远低于我们浪费时间试图让这一切按照您的方式工作。
这就是世界的方式。烧掉桥梁并需要升级。转换数据,或者做一个工具来做,然后不再支持旧版本的做事方式。
如果 C# 程序将数据交给其他应用程序,则不会。其他应用程序不应直接访问属于该应用程序的数据,对吗?
回答by Marc Gravell
For transfer and offline storage, serialization is fine; but for active use, some kind of database is far preferable.
对于传输和离线存储,序列化很好;但是对于主动使用,某种数据库是更可取的。
Typically (as you say), without a database, you need to deserialize the entire stream to perform any query, which makes it hard to scale. Add the inherent issues with threading etc, and you're asking for pain.
通常(如您所说),如果没有数据库,您需要反序列化整个流以执行任何查询,这使得扩展变得困难。添加线程等的固有问题,您会感到痛苦。
Some of your other pain points about serialization aren't all true - as long as you pick wisely. Obviously, BinaryFormatter
is a bad choice for portability and versioning, but "protocol buffers" (Google's serialization format) has versions for Java, C++, C#, and a lot of others, and is designed to be version tolerant.
你关于序列化的其他一些痛点并不都是真的 - 只要你明智地选择。显然,BinaryFormatter
对于可移植性和版本控制来说,这是一个糟糕的选择,但是“协议缓冲区”(Google 的序列化格式)具有 Java、C++、C#和许多其他版本的版本,并且被设计为具有版本容错性。
回答by Peter
It depends on what you want to serialize of course. In some cases serialization is ridicilously easy.
当然,这取决于您想要序列化的内容。在某些情况下,序列化非常容易。
(I once wrote kind of a timeline program in Java, where you could draw en drag around and resize objects. If you were ready you could save it in file (like myTimeline.til). On that momenet hundreds of objects where saved, their position on the canvas, their size, their colors, their innertexts, their special effects,...
(我曾经用 Java 编写了一种时间线程序,您可以在其中绘制并拖动对象并调整其大小。如果您准备好了,您可以将其保存在文件中(例如 myTimeline.til)。在那一刻,保存了数百个对象,它们的在画布上的位置,它们的大小,它们的颜色,它们的内在文本,它们的特殊效果,......
You could than ofcourse open myTimeLine.til and work further.
你当然可以打开 myTimeLine.til 并进一步工作。
All this only asked a few lines of code. (just made all classes and their dependencies serializable) and my coding time took less than 5 minutes, I was astonished myself! (it was the first time I used serialization ever)
这一切只问了几行代码。(只是使所有类及其依赖项可序列化)而且我的编码时间不到 5 分钟,我自己也很惊讶!(这是我第一次使用序列化)
Working on a timeline you could also 'saveAs' for different versions and the 'til' files where very easy to backup and mail.
在时间轴上工作,您还可以为不同版本的“另存为”以及非常容易备份和邮寄的“til”文件。
I think in my particular case it would be a bit idiot to use databases. But that's of course for document-like structures only, like Word to name one.)
我认为在我的特殊情况下使用数据库会有点白痴。但这当然仅适用于类似文档的结构,例如 Word。)
My point thus first : there are certainly several scenarios in which databases wouldn't be the best solution.Serialization was not invented by developers just because they were bored.
我的观点首先是:当然有几种情况数据库不是最佳解决方案。序列化不是开发人员因为无聊而发明的。
- Not true if you use XMLserialization or SOAP
- Not quite relevant anymore
- Only if you are not carefull, plenty of 'best practices' for that.
- Only if you want it to be problematic, see 1
- 如果您使用 XMLserialization 或 SOAP,则不正确
- 不再相关
- 只有当你不小心时,才会有大量的“最佳实践”。
- 仅当您希望它有问题时,请参阅 1
Of course serialization has besides the speed of implementation other important advantages like not needing a database at all in some cases!
当然,除了实现速度之外,序列化还有其他重要优势,例如在某些情况下根本不需要数据库!
回答by David Pope
You didn't say what kind of data it is -- much depends on your performance, simultaneity, installation, security, and availability/centralization requirements.
您没有说明它是什么类型的数据——很大程度上取决于您的性能、同时性、安装、安全性和可用性/集中化要求。
If this data is very large (e.g. many instances of the objects in question), a database can help performance via its indexing capabilities. Otherwise it probably hurts performance, or is indistinguishable.
If your app is being run by multiple users simultaneously, and they may want to write this data, a database helps because you can rely on transactions to ensure data integrity. With file-based persistence you have to handle that yourself. If the data is single-user or single-instance, a database is very likely overkill.
If your app has its own soup-to-nuts installation, using a database places an additional burden on the user, who must set up and maintain (apply patches etc.) the database server. If the database can be guaranteed to be available and is handled by someone else, this is less of an issue.
What are the security requirements for the data? If the data is centralized, with multiple users (either simultaneous or sequential), you may need to manage security and permissions on the data. Without seeing the data it's hard to say whether it would be easier to manage with file-based persistence or a database.
If the data is local-only, many of the above questions about the data have answers pointing toward file-based persistence. If you need centralized access, the answers generally point toward a database.
如果此数据非常大(例如,相关对象的许多实例),数据库可以通过其索引功能提高性能。否则它可能会损害性能,或者无法区分。
如果您的应用程序由多个用户同时运行,并且他们可能想要写入这些数据,那么数据库会有所帮助,因为您可以依靠事务来确保数据完整性。使用基于文件的持久性,您必须自己处理。如果数据是单用户或单实例,那么数据库很可能是矫枉过正。
如果您的应用程序有自己的完整安装,使用数据库会给用户带来额外的负担,用户必须设置和维护(应用补丁等)数据库服务器。如果数据库可以保证可用并且由其他人处理,那么这不是一个问题。
数据的安全要求是什么?如果数据是集中的,有多个用户(同时或顺序),您可能需要管理数据的安全性和权限。如果没有看到数据,很难说使用基于文件的持久性或数据库来管理是否更容易。
如果数据是仅限本地的,那么上述有关数据的许多问题的答案都指向基于文件的持久性。如果您需要集中访问,答案通常指向数据库。
My guess is that you probably don't need a database, based solely on the fact that you're asking about it mainly from a programming-convenience perspective and not a data-requirements perspective. Serialization, especially in .NET, is highly customizable and can be easily tailored to persist only the essential pieces you need. There are well-known best practicesfor versioning this data as well, so I'm not sure there's an advantage on the database side from that perspective.
我的猜测是,您可能不需要数据库,这完全基于您主要从编程方便的角度而不是从数据需求的角度来询问它的事实。序列化,尤其是在 .NET 中,是高度可定制的,可以轻松定制以仅保留您需要的基本部分。对这些数据进行版本控制也有众所周知的最佳实践,所以我不确定从这个角度来看数据库方面是否有优势。
About cross-platform concerns: If you do not know for certainthat cross-platform functionality will be required in the future, do not build for it now. It's almost certainly easier overall to solve that problem when the time comes (migration etc.) than to constrain your development now. More often than not, YAGNI.
关于跨平台问题:如果您不确定将来需要跨平台功能,请不要立即构建。在时机成熟时(迁移等)解决该问题总体上几乎肯定比现在限制您的开发更容易。通常情况下,YAGNI。
About sharing data between parts of the application: That should be architected into the application itself, e.g. into the classes that access the data. Don't overload the persistence mechanism to also be a data conduit between parts of the application; if you overload it that way, you're turning the persisted state into a cross-object contract instead of properly treating it as an extension of the private state of the object.
关于在应用程序的各个部分之间共享数据:这应该构建到应用程序本身中,例如访问数据的类。不要让持久化机制过载,使其成为应用程序各部分之间的数据管道;如果以这种方式重载它,就会将持久状态转换为跨对象契约,而不是正确地将其视为对象私有状态的扩展。
回答by Joe
Just make sure you have a component that handles saving/loading state with a clean interface to the rest of your application. Then whatever choice you make for persistence can easily be revisited later.
只需确保您有一个组件可以处理保存/加载状态,并为应用程序的其余部分提供干净的界面。然后,您为持久性所做的任何选择都可以在以后轻松地重新审视。
Serializing an object graph to a file might be a good quick and dirty initial solution that is very quick to implement.
将对象图序列化为文件可能是一个很好的快速而肮脏的初始解决方案,并且实施起来非常快。
But if you start to run into issues that make a database a better choice you can plug in a new version with little or no impact on the rest of the application.
但是,如果您开始遇到使数据库成为更好选择的问题,您可以插入一个新版本,而对应用程序的其余部分几乎没有影响。
回答by Joe
Yes propably true. The downside is that you must retrieve the whole object which is like retrieving all rows from a table. And if it's big it will be a downside. But if it ain't so big and with my hobbyprojects they are not, so maybe they should be a perfect match?
是的,应该是真的。缺点是您必须检索整个对象,就像从表中检索所有行一样。如果它很大,那将是一个缺点。但如果它不是那么大,而且我的业余爱好项目也不是,那么也许它们应该是完美的搭配?