Ruby Marshal Serialization
Marshal is the core library of Ruby. It can serialize and save some objects into a file in binary form, and then load it from the file and rebuild it into an object, that is, deserialization.
Marshal has no problem in serializing and saving basic data such as numerical values, strings, arrays, and boolean values.
But not all types of data can be serialized. Marshal performs some operations during the process of loading and rebuilding an object from a serialized file, but some content may be lost in the process of restoring it cannot serialize I0 stream objects and code class objects: Proc objects, singleton objects, anonymous classes and modules, which is its limitation.
The process of serialization and deserialization is very simple:
# a nested arrayarr = [ %w(Perl Python PHP), %w(C C++ Java Golang), %w(Shell Powershell Cmdline) ] # Serialize the arr object to save it to a file('/tmp/', "w") do |file| (arr, file) end # Deserialization('/tmp/') do |file| data = (file) end p data
() You can also specify at most how many nested object levels are allowed to be serialized through the third parameter, that is, depth, if the depth exceeds the depth, an error will be reported. Its default value is -1, which means that the depth is not checked, that is, dump all levels. For example:
arr = [ %w(Perl Python PHP), [ %w(C C++), %(Java Golang) ], #=> 3 layers %w(Shell Powershell Cmdline) ] # Serialize the arr object to save it to a file('/tmp/', "w") do |file| (arr, file, 4) #=> If it is less than 4, an error will be reportedend
If you want to specify what to serialize in an object, or specify what type to serialize it to, you can write it in the classmarshal_dump
andmarshal_load
method. For example, only dump a portion of the data and save it as an array:
class Klass def initialize name, age, height @name = name @age = age @height = height end def marshal_dump [@name, @age] end # Deserialization, arr is an array during serialization # Finally it returns a Klass instance object def marshal_load arr @name, @age = arr end end # Serialize an object of Klass, but it will only contain two attributes: name and ageobj = ("junmajinlong", 23, 170) ('/tmp/','w') do |file| (obj, file) end # Deserialize to get a Klass instance object, and set the name and age propertiesobj1 = ("/tmp/") do |file| file end p obj1 #=> #<Klass:0x00007fffcc0119f8 @name="junmajinlong", @age=23>
Obviously, a height attribute is missing during the above deserialization process. In order to make the object complete, when deserializing, it is necessary to reasonably build a new object based on the results obtained by deserialization. For example, use instance_eval() to build a new object:
def marshal_load arr self.instance_eval do initialize(*arr, 170) end end
Ruby Pstore Storage
Pstore (persistence store) is a standard library for persistent storage in Ruby. It stores data in a key-value file based on Hash data type (binary), where value is the data you want to store, and key is a name for this part of the data.
In Pstore, the key is called root, and each key is a root.
Pstore is transaction-based, so the process of adding, deleting and modifying data multiple times is atomic, and can be committed and rolled back. The transaction will be terminated immediately when commit() and abort(), so the code behind them will not be executed. If commit() or abort() is not specified, it will be saved automatically when exiting transaction.
Because every time you read the store, you have to load part of the file content into memory (until the corresponding key is found), the reading efficiency is not high. Furthermore, every time you write, you need to copy most of the data of the file, so it is even less efficient. Therefore, Pstore is only suitable for data storage scenarios with a small amount of data and a small amount of read and write.
For example, persist to a file:
require 'pstore' s = ('/tmp/') do s["p1"] = {name: "junmajinlong", age: 23, height: 170 } s["p2"] = {name: "junma", age: 22, height: 180} s["p3"] = {name: "jinlong", age: 24} end do # Overwrite p2 s["p2"] = {name: "jinlong", age: 24, height: 170 } end #=> automaticcommit
Read data from store file:
require 'pstore' s = ("/tmp/") p2 = do s["p2"] end p p2 puts
transaction(read_only=false)
You can also specify whether the transaction is read-only. If read-only is set, any modifications to the store within the transaction will throw an error.
There are other auxiliary methods for Pstore:
[KEY] :Get the value of the element,If the element does not exist, returnnil delete() :Delete elements,You can specify the default value parameters when the element does not exist fetch() :Get elements,If the element does not exist,Default error,Default return value can be specified path() :returnpstoreFile path root?() :examinekeyDoes it exist roots() :return所有的key
More AboutRuby serialization and persistent storage (Marshal, Pstore) operation methodPlease check the related links below