Ruby Ternary Operator Structure

Ruby ternary operator structure

When you don't put the parentheses on a method call, Ruby assumes you want everything to the end of the line to be the arguments. That is to say, these calls are equivalent (and invalid):

bool ? puts "true" : puts "false"
bool ? puts("true" : puts "false")

Is the ternary operator ?: defined as a method in Ruby?

Is the ternary operator in Ruby really just a syntactic sugar for if ... then ... else ... end statements?

Yes.

From doc/syntax/control_expressions.rdoc

You may also write a if-then-else expression using ? and :. This ternary if:

input_type = gets =~ /hello/i ? "greeting" : "other"

Is the same as this if expression:

input_type =
if gets =~ /hello/i
"greeting"
else
"other"
end

"According to this book, "every operation is a method call on some object and returns a value." In this sense, if the ternary operator represents an operation, it is a method call on an object with two arguments."

if, unless, while, and until are not operators, they are control structures. Their modifier versions appear in the operator precedence table because they need to have precedence in order to be parsed. They simply check if their condition is true or false. In Ruby this is simple, only false and nil are false. Everything else is true.

Operators are things like !, +, *, and []. They are unary or binary. You can see a list of them by calling .methods.sort on various objects. For example...

2.4.3 :004 > 1.methods.sort
=> [:!, :!=, :!~, :%, :&, :*, :**, :+, :+@, :-, :-@, :/, :<, :<<, :<=, :<=>, :==, :===, :=~, :>, :>=, :>>, :[], :^, :__id__, :__send__, etc...

Note that in Smalltalk, from which Ruby borrows heavily, everything really is a method call. Including the control structures.

How can I use the ternary operator with multiple values?

Since a ternary operator is exactly that (an operator), you can't split it over multiple instructions.

However, blocks make it possible to "squash" multiple instructions into a single expression.

def my_withdraw(pin_number,amount)
puts (
pin_number == @pin ?
begin
@balance -= amount
"Withdrew #{amount}."
end :
pin_error
)
end

Of course, this is completely illegible and I would never recommend you use that sort of syntax in the real world. But for the sake of science, why not.

Ruby ternary operator in erb?

<span style="color:<%= manuscript.uploaded_to_s3? ? 'green' : 'red' %>">

I would advocate a CSS class rather than style attribute 8P:

<span class="<%= manuscript.uploaded_to_s3? ? 'green' : 'red' %>">

Using defined? in a Ternary operator

It should be:

<% defined?(foo) == "local-variable" ? foo : nil %>

From documentation:

... return value provides information about the expression.

>> defined?(foo) == "local-variable"
=> true
>> defined? foo
=> "local-variable"
>> defined? (foo == "local-variable")
=> "method"

Ruby operator precedence

Ruby multiline ternary expression?

You should wrap the expressions in parenthesis:

condition ? (expression1 line 1; expression1 line 2; expression1 line 3) : expression2

You should keep in mind that this reduces readability of your code. You are probably better off using an if/else statement to improve readability. One resource I like to use when reviewing my ruby code is the community style guide. As it says in the introductory paragraph:

This Ruby style guide recommends best practices so that real-world
Ruby programmers can write code that can be maintained by other
real-world Ruby programmers.

Hope this helps

How do you write inline Ruby on Rails ternary operators in an HTML tag with white space?

You can write it like this

<li class="<%= loc == @ruby_var ? "nav-item active" : "nav-item" %>">
# ...
</li>

Note the " outside of the erb expression.

Or you can use tag helper like this

<%= tag.li, class: ["nav-item", (:active if loc == @ruby_var)] do %>
# ...
<% end %>

I like the second option better because I prefer not to mix HTML and ERB when describing a tag.

How to use multiple assignment with a ternary operator?

Here is the correct syntax for multiple assignment using a ternary operator:

foo, bar = baz ? [1, 2] : [3, 4]

The return values for true and false must be wrapped in brackets.

I hope this helps :)

ternary operator based on if else

For something like this you might want to use a simple look-up table to eliminate some of the logic:

EQUIVALENT = {
'Y' => 'guest',
'N' => 'test'
}

if (a.present?)
b = EQUIVALENT[b.value] || b
end

The || b part may not be necessary if non-mapped b values are ignored.

In Ruby, why doesn't ternary operator work when using a puts function inside an each statement?

This is caused by ambiguous arguments. Ruby, unlike many other languages such as JavaScript, is really lax about requiring brackets puts x and puts(x) are equivalent. Where this breaks down is when it's not clear which are arguments, and which are part of other syntax.

For example, if f is a method that takes 1-3 arguments and x and y are variables, then what is the meaning of:

f x, f x, y

Is that f(x, f(x,y)), f(x), f(x), y or f(x, f(x), y)? Ruby throws an error rather than presume the wrong thing.

Easy fix is to eliminate the duplication of effort here and use a single puts with a ternary used to determine the value:

array = [1,2,3]
array.each { |x| puts x > 2 ? "lower" : "higher"}

Now it works because there's no ambiguity on arguments, there's only one method call so it's easy.



Related Topics



Leave a reply



Submit