_If you wish to report errors or suggest improvements for this FAQ,
please go to our
[GitHub repository](https://github.com/ruby/www.ruby-lang.org/)
and open an issue or pull request._


## Синтаксис

### У чому різниця між безпосереднім значенням і посиланням?
{: #immediate}

<div class="not-prose bg-ruby-100 dark:bg-ruby-800 rounded-lg p-8 my-6">
  <div class="flex items-start gap-3">
    <svg class="w-6 h-6 text-ruby-700 dark:text-ruby-200 flex-shrink-0 mt-0.5" fill="currentColor" viewBox="0 0 20 20">
      <path fill-rule="evenodd" d="M8.485 2.495c.673-1.167 2.357-1.167 3.03 0l6.28 10.875c.673 1.167-.17 2.625-1.516 2.625H3.72c-1.347 0-2.189-1.458-1.515-2.625L8.485 2.495zM10 5a.75.75 0 01.75.75v3.5a.75.75 0 01-1.5 0v-3.5A.75.75 0 0110 5zm0 9a1 1 0 100-2 1 1 0 000 2z" clip-rule="evenodd"/>
    </svg>
    <p class="text-sm text-ruby-700 dark:text-ruby-200 italic">
      This section or parts of it might be out-dated or in need of confirmation.
    </p>
  </div>
</div>


`Fixnum`, `true`, `nil` і `false` реалізовані як безпосередні значення.
Для безпосередніх значень змінні зберігають самі об’єкти, а не
посилання на них.

Для таких об’єктів не можна визначати singleton-методи. Два `Fixnum`
з однаковим значенням завжди представляють той самий екземпляр об’єкта,
тому (наприклад) змінні екземпляра для `Fixnum` зі значенням `1`
спільні для всіх `1` у системі. Це робить неможливим визначення
singleton-методу лише для одного з них.

### У чому різниця між `nil` і `false`?

Спочатку про схожість: `nil` і `false` — єдині два об’єкти,
які в булевому контексті оцінюються як `false`.
(Інакше кажучи: це єдині «falsy»-значення, усі інші
об’єкти — «truthy».)

Однак `nil` і `false` — це екземпляри різних класів
(`NilClass` і `FalseClass`) і в інших місцях поводяться по-різному.

Ми рекомендуємо, щоб предикатні методи (ті, чия назва закінчується знаком
питання) повертали `true` або `false`. Інші методи, яким потрібно
позначити невдачу, мають повертати `nil`.

### Чому порожній рядок не є `false`?

П: Порожній рядок (`""`) повертає `true` в умовному виразі!
У Perl це `false`.

В: Але Ruby — не Perl ;-). Все дуже просто: у Ruby лише `nil`
і `false` є хибними в умовних контекстах.

Можна використати `empty?`, порівняти рядок із `""` або порівняти його
`size` чи `length` із `0`, щоб дізнатися, чи рядок порожній.

### Що означає `:name`?

Двокрапка перед іменем створює об’єкт Symbol, який однозначно відповідає
ідентифікатору. Протягом виконання програми для певного імені або рядка
буде створено той самий об’єкт Symbol. Символи також можна створити
за допомогою `"name".intern` або `"name".to_sym`.

Об’єкти Symbol можуть представляти ідентифікатори методів, змінних тощо.
Деякі методи, такі як `define_method`, `method_missing` або `trace_var`,
потребують символ. Інші методи, наприклад `attr_accessor`, `send`
або `autoload`, також приймають рядок.

Оскільки вони створюються лише один раз, символи часто використовують як
ключі хешів. Рядкові ключі хешів створювали б новий об’єкт для кожного
використання, спричиняючи певні витрати пам’яті.
Є навіть спеціальний синтаксис для ключів-символів:

~~~
person_1 = { :name => "John", :age => 42 }
person_2 = { name: "Jane", age: 24 }        # alternate syntax
~~~

Символи також можна використовувати як значення переліків
або для присвоєння унікальних значень константам:

~~~
status = :open  # :closed, ...

NORTH = :NORTH
SOUTH = :SOUTH
~~~

### Як отримати значення символу?

Щоб отримати значення змінної, що відповідає символу, можна використати
`symbol.to_s` або `"#{symbol}"`, щоб отримати ім’я змінної, а потім
виконати це через `eval` у відповідній області видимості й отримати
вміст змінної:

~~~
a = "This is the content of `a'"
b = eval("#{:a}")
a.object_id == b.object_id  # => true
~~~

Також можна використати

~~~
b = binding.local_variable_get(:a)
~~~

Якщо ваш символ відповідає імені методу, можна використати `send`:

~~~
class Demo
  def hello
    "Hello, world"
  end
end

demo = Demo.new
demo.send(:hello)
~~~

Або можна використати `Object#method`, щоб повернути відповідний об’єкт
`Method`, який потім можна викликати:

~~~
m = demo.method(:hello)  # => #<Method: Demo#hello>
m.call                   # => "Hello, world"
~~~

### Чи є `loop` керувальною структурою?

Хоча `loop` виглядає як керувальна структура, насправді це метод,
визначений у `Kernel`. Блок, що йде за ним, створює нову область
видимості для локальних змінних.

### У Ruby немає циклу з перевіркою в кінці

П: У Ruby немає конструкції `do { ... } while`, тож як реалізувати
цикли, що перевіряють умову наприкінці?

Клеменс Гінце каже: можна використати поєднання `begin ... end`
та модифікаторів `while` або `until`, щоб досягти того самого ефекту:

~~~
i = 0
begin
  puts "i = #{i}"
  i += 1
end until i > 4
~~~

Виведе:

~~~
i = 0
i = 1
i = 2
i = 3
i = 4
~~~

### Чому не можна передати літерал хеша до методу: `p {}`?

`{}` розбирається як блок, а не як конструктор `Hash`. Можна змусити
`{}` трактуватися як вираз, явно вказавши, що це параметр: `p({})`.

### Не можу змусити `def pos=(val)` працювати!

У мене є такий код, але я не можу використовувати метод `pos = 1`.

~~~
def pos=(val)
  @pos = val
  puts @pos
end
~~~

Методи з `=` наприкінці потрібно викликати з явним отримувачем
(без отримувача ви просто присвоюєте значення локальній змінній).
Викликайте його як `self.pos = 1`.

### У чому різниця між `'\1'` і `'\\1'`?

Вони мають те саме значення. У рядку в одинарних лапках перетворюються
лише `\'` і `\\`, інші комбінації залишаються незмінними.

Проте в рядку в подвійних лапках `"\1"` — це байт `\001`
(вісімковий бітовий шаблон), тоді як `"\\1"` — це рядок із двох символів:
зворотний слеш і символ `"1"`.

### У чому різниця між `..` і `...`?

`..` включає праву межу діапазону, `...` — ні:

~~~
(5..8).to_a   # => [5, 6, 7, 8]
(5...8).to_a  # => [5, 6, 7]
~~~

### У чому різниця між `or` і `||`?

П: `p(nil || "Hello")` друкує `"Hello"`, тоді як `p(nil or "Hello")`
дає синтаксичну помилку. Чому?

В: `or` має дуже низький пріоритет, `p( (nil or "Hello") )` спрацює.

Пріоритет `or`, наприклад, також нижчий, ніж у `=`,
тоді як `||` має вищий пріоритет:

~~~
foo = nil || "Hello"  # parsed as: foo = (nil || "Hello")
foo  # => "Hello"

# but perhaps surprisingly:

foo = nil or "Hello"  # parsed as: (foo = nil) or "Hello"
foo  # => nil
~~~

`or` (і так само `and`) найкраще використовувати **не** для поєднання
булевих виразів, а для керування потоком виконання, наприклад

~~~
do_something  or raise "some error!"
~~~

де `do_something` повертає `false` або `nil`, коли стається помилка.

### Чи є в Ruby вказівники на функції?

Об’єкт `Proc`, створений `Proc.new`, `proc` або `lambda`, можна зберегти
в змінній, тож така змінна може вважатися вказівником на функцію. Також
можна отримати посилання на методи конкретного екземпляра об’єкта
за допомогою `object.method`.

### У чому різниця між `load` і `require`?

`load` завантажує і виконує програму Ruby (`*.rb`).

`require` також завантажує програми Ruby, але ще й бінарні модулі
розширень Ruby (спільні бібліотеки або DLL). Крім того, `require`
гарантує, що один і той самий компонент не буде завантажено більше
одного разу.

### Чи є в Ruby обробка винятків?

Ruby підтримує гнучку схему обробки винятків:

~~~
begin
  statements which may raise exceptions
rescue [exception class names]
  statements when an exception occurred
rescue [exception class names]
  statements when an exception occurred
ensure
  statements that will always run
end
~~~

Якщо в блоці `begin` виникає виняток, виконується `rescue` із
відповідною назвою винятку. Блок `ensure` виконується незалежно від того,
чи стався виняток. Частини `rescue` та `ensure` можна опустити.

Якщо для `rescue` не вказано клас винятку, мається на увазі
`StandardError`, і перехоплюються винятки, що перебувають у відношенні
`is_a?` до `StandardError`.

Цей вираз повертає значення блоку `begin`.

Останній виняток доступний через глобальну змінну `$!`
(і тому його тип можна визначити за допомогою `$!.type`).
