ruby Rails respond_to?方法在IF.. AND语句

fdbelqdn  于 2023-04-29  发布在  Ruby
关注(0)|答案(2)|浏览(89)

我正在从LDAP服务器获取用户列表:

filter_person = Net::LDAP::Filter.eq("objectClass", "person")
treebase = "ou=people,dc=rocketfuel,dc=com"
ldap.search(:base => treebase, :filter => filter_person, :scope => Net::LDAP::SearchScope_SingleLevel, :attributes => ['uid', 'sshpublickey']) do |entry|
  if users_uids.include?(entry.uid[0].to_s)
    p entry.uid[0].to_s
  end
 end

此代码失败,但出现以下异常:

NoMethodError: undefined method `uid' for #<Net::LDAP::Entry:0x00000000074bf558>

这是预期的(一些用户没有UID)。但是我不太清楚为什么如果我把if语句改为:

if entry.respond_to?(:uid) and users_uids.include?(entry.uid[0].to_s)
  p entry.uid[0].to_s
end

我希望它能通过相同的错误(如if ... and语句同时计算),但它实际上工作得很好
为什么当我把entry.respond_to?(:uid)添加到相同的条件表达式时,entry.uid[0]没有引发相同的异常?

laawzig2

laawzig21#

entry上没有定义uid时,调用entry.uid会引发异常。如果entry上没有定义uid方法,则entry.respond_to?(:uid)返回错误。
这意味着它有效是因为

if entry.respond_to?(:uid) and users_uids.include?(entry.uid[0].to_s)

在第一个条件中计算为false,并且不再检查第二个条件,因为它不会改变结果。
这是一个叫做Short-Circuit evaluation的特性,它存在于大多数语言中。

gojuced7

gojuced72#

And操作不会在所有情况下执行两边
在这个例子中,它首先计算左侧,只有当结果不同于falsenil时,它才继续计算右侧部分。
因此,如果entry.respond_to?(:uid)计算为nil,则跳过右侧部分users_uids.include?(entry.uid[0].to_s)

相关问题