假设我有一个类似的课程,如下所示:
class User
attr_accessor :name, :age
def initialize(name, age)
@name, @age = name, age
end
end
现在,将用户保存为单个文件中 User 类的编组实例或者使用带有 ORM 的 Sqlite 数据库会更快吗?基于文件的数据存储有哪些缺点?
以下是在 SSD 上执行的基准测试结果。按照您的意愿解释它们。对于非常简单的查询和数据,将整个数据集编组并加载到内存中显得更快:
Rehearsal ---------------------------------------------------------------
Storing in DB 0.080000 0.000000 0.080000 ( 0.085909)
Marshalling to Disk 0.010000 0.000000 0.010000 ( 0.004340)
Fetching marshal 0.000000 0.000000 0.000000 ( 0.002288)
Fetching records from DB 5.530000 0.130000 5.660000 ( 5.657053)
Fetching records from Array 0.350000 0.000000 0.350000 ( 0.347798)
Find one record from DB 0.320000 0.020000 0.340000 ( 0.336068)
Find one record from Array 0.260000 0.000000 0.260000 ( 0.258766)
------------------------------------------------------ total: 6.700000sec
user system total real
Storing in DB 0.080000 0.000000 0.080000 ( 0.079717)
Marshalling to Disk 0.000000 0.000000 0.000000 ( 0.002595)
Fetching marshal 0.000000 0.000000 0.000000 ( 0.001466)
Fetching records from DB 10.830000 0.230000 11.060000 ( 11.041669)
Fetching records from Array 0.340000 0.000000 0.340000 ( 0.335473)
Find one record from DB 0.320000 0.010000 0.330000 ( 0.336917)
Find one record from Array 0.260000 0.000000 0.260000 ( 0.255746)
这是基准:
require 'benchmark'
require 'sequel'
class User
attr_reader :name, :age
def initialize(name, age)
@name, @age = name, age
end
def to_hash; {name:@name, age:@age}; end
end
db_array = 1000.times.map{ User.new "name#{rand 1000}", rand(1000) }
db_array << User.new( "unique", 42 )
DBFILE = 'users.db'; MARSHAL = 'users.marshal'
File.delete(DBFILE) if File.exists?(DBFILE)
DB = Sequel.sqlite(DBFILE)
DB.create_table(:users){ column(:name,:string); column(:age,:int) }
db_users = DB[:users]
Benchmark.bmbm do |x|
x.report('Storing in DB'){ db_users.multi_insert db_array.map(&:to_hash) }
x.report('Marshalling to Disk'){ File.open(MARSHAL, 'w'){ |f| f << Marshal.dump(db_array) } }
x.report('Fetching marshal'){ db_array = Marshal.load(File.open(MARSHAL,'r'){|f| f.read }) }
query = db_users.select{ name > "name500" }
x.report('Fetching records from DB'){ 1000.times{ query.all } }
x.report('Fetching records from Array'){ 1000.times{ db_array.select{ |u| u.name > "name500" } } }
x.report('Find one record from DB'){ 1000.times{ db_users[name:'unique'] } }
x.report('Find one record from Array'){ 1000.times{ db_array.find{ |u| u.name == "unique" } } }
end
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)