In Ruby, how do =begin and =end create a multi-line comment, and why do most Rubyists use consecutive # lines instead?
answer
- two comment forms
- markers must start at column 0
- indented =begin is a SyntaxError
- embedded document meets end of file
- editors toggle # lines
basics
~20 sEverything between =begin and =end is ignored, but both markers must start at the very beginning of their own lines, so they cannot be indented inside a class or method. Most Rubyists put # on each line instead, which works at any indentation.
solid answer
~40 sRuby has two comment forms. `#` starts an **inline comment** that runs to the end of the line; it can stand alone, follow code, or be indented. `=begin` ... `=end` is a **block comment**, also called an embedded document: every line between the markers is ignored, and text may follow `=begin` on the same line. Both markers must start at **column 0**, so an indented `=begin` inside a class body is a `SyntaxError`, and a missing `=end` fails with `embedded document meets end of file`. Because Ruby code is almost always indented, block comments break its visual structure, which is why most code and style guides use consecutive `#` lines that editors add and remove in one keystroke. A `#` inside a string literal is just a character, not the start of a comment.
code
ruby · 17 lines# Calculates the fine for a late loan.
# Rates are per day, capped at the book's price.
class LibraryLoan
DAILY_RATE = 25 # cents
def fine(days_late)
# old_rate * days_late
DAILY_RATE * days_late
end
end
=begin
This whole block is ignored.
Both markers start at column 0.
=end
puts "Shelf #3" # prints: Shelf #3go deeper
Know both comment forms and that =begin and =end must start at the beginning of a line.
Explain why block comments are rare in practice, and recognise the SyntaxError from an indented or unterminated =begin.
Prefer deleting commented-out code over preserving it, and keep comments where tools such as documentation generators expect them.
Keep comment style out of debates by leaving it to the team's linter configuration, so reviews focus on what the comments say.
## Two ways to comment Ruby recognises two comment syntaxes, and both are ignored by the interpreter. | Form | Starts with | Ends at | Can be indented? | |---|---|---|---| | inline comment | `#` | the end of the line | yes | | block comment (embedded document) | a line beginning `=begin` | a line beginning `=end` | no | ## Inline comments with # - A `#` outside a string or regexp literal starts a comment that runs to the end of the line. - It can sit on its own line, at any indentation, or after code: `renew! # raises at the limit`. - Several consecutive `#` lines form a multi-line comment, which is how nearly all Ruby code writes one. - A `#` **inside a string** is ordinary text: `puts "Shelf #3" # restock` prints `Shelf #3`. ## Block comments with =begin and =end The rules are strict: 1. `=begin` must be at the very start of a line, with no leading spaces. 2. `=end` must also start at column 0, on its own line. 3. Everything between them is ignored, including lines that look like code. 4. Text may follow `=begin` on the same line (`=begin notes`), and it is ignored too. 5. If the file ends before `=end`, parsing fails with `embedded document meets end of file`. Rule 1 is the practical problem. Code inside a class or method is indented, so commenting out part of a method with `=begin` requires pulling the markers back to column 0: ```ruby class LibraryLoan def fine =begin old_rate * days_overdue =end 0 end end ``` Indenting the markers to match the code (` =begin`) makes the whole file a `SyntaxError`. ## Why # lines win - **Indentation**: `#` lines follow the code's indentation, so the file keeps its shape. - **Editor support**: every Ruby-aware editor comments and uncomments a selection by adding or removing `#`. - **Visibility**: each commented line is marked, so a reader scrolling through a long block never mistakes it for live code. - **Linting**: community style guides and linters prefer `#` and flag block comments. - **Documentation tools** read the `#` comments directly above a method or class, so the everyday form is also the documented one. ## Things that look like comments but are not - **Magic comments** such as `# frozen_string_literal: true` are written with `#`, but the parser reads them as directives when they appear in the right place at the top of a file. - **`__END__`** on a line by itself ends the program source: nothing after it is parsed, so it cannot comment out code in the middle of a file. - **A shebang line** (`#!/usr/bin/env ruby`) is a `#` comment to the parser; the operating system uses it to pick the interpreter, and the `ruby` command also reads any options written on it. ## How the question is usually asked - **"Does Ruby have multi-line comments?"** Yes, `=begin`/`=end`, with the column-0 rule; in practice consecutive `#` lines. - **"Why does this file fail after I added =begin?"** The marker was indented, or `=end` is missing and the parser reached the end of the file. - **"Is `#` inside a string a comment?"** No; only a `#` outside string and regexp literals starts one. - **"What is the first line `#!/usr/bin/env ruby`?"** A shebang: a comment to the parser, an instruction to the operating system when the file is executed directly. A candidate who answers the first question with only `=begin` and never mentions `#` lines usually has not read much real Ruby code. ## In practice Reach for `#` lines by default. `=begin`/`=end` is legal and occasionally seen at the top of old scripts, but in modern code it mostly appears in interview questions about Ruby's syntax. Commented-out code itself is better deleted, since version control keeps the history.
- What happens if a file has =begin but no matching =end?The parser treats everything after `=begin` as part of the embedded document, reaches the end of the file still inside it, and fails with a `SyntaxError` whose message says the embedded document meets end of file. Nothing in the file runs.
- Can __END__ be used to comment out a block of code?Not in the middle of a file. `__END__` on its own line ends the program source, so everything after it, including any `end` keywords the code above still needs, is never parsed. It is meant for attaching data to a script, not for commenting.
saying these in an interview costs you the question
- =begin and =end can be indented to line up with the code
- A # inside a double-quoted string starts a comment
- Ruby has no block-comment syntax at all
- __END__ closes a block comment opened earlier