rubyguides

Array#first

arr.first(n=nil) -> obj or array

Array#first retrieves the leading element from a list. It provides a clean, readable way to access elements without using index notation.

That small change in syntax matters when the front of the array carries meaning. It keeps the intent obvious, whether you are peeking at a queue, previewing a sorted list, or just grabbing the first few items for display.

Syntax

arr.first      # returns first element
arr.first(n)   # returns first n elements as array

The method has a simple API: a single optional integer argument controls whether you get one element or many, and the return type adjusts accordingly. This is more intuitive than having separate methods for single-element access and multi-element slicing because the caller’s intent is visible right in the argument.

Parameters

ParameterTypeDefaultDescription
nIntegernilWhen provided, returns an array of the first n elements instead of a single element

Examples

Basic usage

fruits = ["apple", "banana", "cherry", "date"]

# Get the first element
fruits.first
# => "apple"

# Get first n elements
fruits.first(2)
# => ["apple", "banana"]

This is the clearest way to see what first returns, because the front of the array is visible right in the example. When the reader already knows the ordering of the data, the method call reads like a simple request instead of a lookup trick.

With empty arrays

empty = []

# Single element returns nil on empty array
empty.first
# => nil

# With n parameter returns empty array
empty.first(3)
# => []

Those return values are useful because they let the next step decide how to respond. A nil can mean “nothing to process”, while an empty array can still flow through code that expects a collection.

The return values from first on an empty array are carefully designed to avoid exceptions. Getting nil for a single-element lookup and an empty array for a slice means your code can often proceed without explicit empty checks, especially when the downstream logic already handles nil or empty collections gracefully.

With various data types

# Works with any object types
mixed = [42, "hello", :symbol, [1, 2], { key: "value" }]

mixed.first
# => 42

mixed.first(3)
# => [42, "hello", :symbol]

Mixing types in one array is common in Ruby, and first does not care what the elements are. The method only needs the order, not a shared class or interface.

These examples show that first works identically whether the array holds integers, strings, symbols, nested arrays, or hashes. The method only depends on position, not type, which makes it a universal tool for any ordered collection in Ruby code.

Common patterns

Check if array has elements

# Common pattern: check presence before accessing
if array.any?
  first_item = array.first
end

The guard-check pattern with any? is a common defensive idiom, but first already handles the empty case gracefully by returning nil. If your downstream code can handle nil, you can often skip the guard and let first communicate “nothing here” through its return value directly.

Get extremes of sorted data

# Often used with sorted data
scores = [95, 87, 92, 88, 79, 91]

# Or using first after sorting
sorted = scores.sort
lowest = sorted.first

After sorting, first gives you the smallest value and last gives you the largest, making the pair a natural way to express min/max without calling separate methods. The pattern works with any sortable data and stays readable because it mirrors the physical idea of a sorted list where the extremes sit naturally at each end of the collection.

Preview large datasets

# Preview first items without loading entire dataset
logs = ["2024-01-01", "2024-01-02", "2024-01-03", "2024-01-04", "2024-01-05"]

puts "First 3 entries:"
logs.first(3).each { |log| puts "  #{log}" }

That pattern is handy because it keeps the preview logic and the display logic separate. first(3) narrows the data, and each handles formatting without making the array access harder to read.

The preview-then-queue pattern is common in command-line tools and log viewers that need to show the first few entries before processing the full list. first(n) handles the preview cleanly without disturbing the original array, so the queue logic that follows can still access the complete sequence.

Queue operations

# First element often serves as queue front
queue = ["task1", "task2", "task3"]
next_task = queue.first
# => "task1"

In queue-like code, first is often the read-only counterpart to shift. It tells you what is coming next without removing anything, which is useful when another part of the program still needs to process the same list.

Error cases

This method never raises exceptions:

# Single element access returns nil
[].first   # => nil

# With n parameter returns empty array
[].first(5)  # => []

# n greater than array length returns all elements
[1, 2].first(10)
# => [1, 2]

Use first when the front matters

first is most useful when the beginning of the array carries meaning. That might be the next job in a queue, the earliest item in a sorted list, or just a quick preview of a larger dataset. The method keeps the call site short and readable, which is often the real reason to prefer it over direct index access. Readers can see the intent immediately: the code wants the leading element or the leading slice, not an arbitrary position buried in the middle.

Handle empties without ceremony

One of the nicest parts of first is that it gives a predictable answer for empty arrays. A single-item lookup returns nil, and asking for a slice returns an empty array. That means your code can often move forward without extra branching, especially when the next step already knows how to deal with nil or an empty collection. This is a small detail, but it makes array handling feel smoother in everyday Ruby code.

Pair it with ordered data

first feels especially natural once the array is sorted or built in a meaningful order. It can show the top record, preview the next batch, or pull the oldest item from a queue-like list. When used with sort, sort_by, or take, it becomes part of a simple sequence: arrange the data, choose the front, then keep moving. That pattern reads well because each step says exactly what it is doing without extra noise.

See Also