开发者

what does !! do in ruby?

开发者 https://www.devze.com 2022-12-16 12:06 出处:网络
I am using some code that uses this syntax (restful authentication). def logged_in? !!current_user() end

I am using some code that uses this syntax (restful authentication).

def logged_in?
  !!current_user()
end

Tried googling for this but it jus开发者_如何学Got seems to ignore "!!", will accept an answer that can tell me how to find info about searching for strings such as !! in google.


It's double negation. The first ! converts it to false if current_user is not nil or false. After that it converts it to true. So the result is always a boolean value and not the value of current_user. The result is always true if current_user is not false or nil. Otherwise it's false.


It's the negation operator, !, twice. This gives a value that has the same truth value, but is explicitly only a boolean.

In Ruby, there are many values that are considered to be "true" (anything besides false and nil), and a couple that are considered to be "false" (both false and nil). The first negation converts all true values to false, and all false values to true. The second negation then reverses that, leaving you with a value that has the same truth value as the original, but only allowing the actual values true or false.

This can be helpful if you don't want people to use logged_in? as a way to access the current user, but instead you want it to just return a boolean.

It it equivalent to the more explicit and verbose:

def logged_in?
  if current_user()
    true
  else
    false
  end
end


This article seems to use the same code:

http://toolmantim.com/articles/bangbang_your_nil_is_dead

Basically, it looks like it's just meant to apply the not (!) operator twice -- essentially forcing the method to return true or false instead of true, false, or nil.

That is, if @current_user is nil, calling

def logged_in?
  @current_user()
end

will return nil. Changing it to (single bang)

def logged_in?
  !@current_user()
end

will return true, and changing further to (double bang)

def logged_in?
  !!@current_user()
end

will return false -- which is more applicable (and usable) than nil.

Another way to write it would be:

def logged_in?
  !@current_user().nil?
end

but that doesn't cover the case when @current_user is false, and I think the !! is nicer to look at.


The blog post covers it:

http://toolmantim.com/articles/bangbang_your_nil_is_dead

0

精彩评论

暂无评论...
验证码 换一张
取 消