ruby-on-rails – .尝试vs \u0026\u0026表现
发布时间:2020-12-17 02:47:48 所属栏目:百科 来源:网络整理
导读:假设我有一个来自SQL查询的传入值,如下所示: grok = Foo.select(:foo_attr1,:foo_attr2).first foo_attr2是一个可以为空的字段.现在假设我需要对输出进行处理(如果存在的话). krug = grok.foo_attr2.try(:bar).try(:baz)gnar = grok.foo_attr2 grok.foo_att
假设我有一个来自SQL查询的传入值,如下所示:
grok = Foo.select(:foo_attr1,:foo_attr2).first foo_attr2是一个可以为空的字段.现在假设我需要对输出进行处理(如果存在的话). krug = grok.foo_attr2.try(:bar).try(:baz) gnar = grok.foo_attr2 && grok.foo_attr2.bar.baz # Assumes bar will always return output that can be baz'd 这两个操作中哪一个更好用,为什么? 解决方法
使用gnar = grok.foo_attr2&& grok.foo_attr2.bar.baz肯定会更快,因为它使用Ruby的逻辑运算符完成.虽然Rails引入了
try ,但还有其他if-else条件检查.来自代码:
# File activesupport/lib/active_support/core_ext/object/try.rb,line 41 def try(*a,&b) if a.empty? && block_given? yield self else public_send(*a,&b) if respond_to?(a.first) end end 好吧,这是一个基准,以准确显示我想说的内容: class Object def try(*a,&b) if a.empty? && block_given? yield self else public_send(*a,&b) if respond_to?(a.first) end end end class Foo attr_reader :a def initialize(a = nil) @a = a end end require "benchmark" bar = Foo.new baz = Foo.new(1) n = 10000000 Benchmark.bm(40) do |x| x.report("try"){ n.times { bar.a.try(:class).try(:to_s) } } x.report("&& "){ n.times { baz.a && baz.a.class.to_s } } end 结果是: user system total real try 10.800000 0.030000 10.830000 ( 10.829770) && 3.940000 0.010000 3.950000 ( 3.944375) (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |