0

I have a question about using foreach loops in Ruby.

I want to display documents and am using a foreach loop in order to display these documents. It returns an error with the i variable inside of data["response"]["docs"][i]["topic"] which is a JSON string I am iterating over.

I do not understand why that is. Can anyone tell me what I am doing wrong?

If I simply do data["response"]["docs"][0]["topic"] it works fine but not with the i. Why is that?

<%
(0..10).each do |i|
%>
<%= i %> <br/>
<%= data["response"]["docs"][i]["topic"] %> 
<%
end
%>
1
  • 1
    Rather than (0..10) consider using n.times where n is the number of times you want to loop. It's much more readable and understandable. Commented Jul 21, 2016 at 18:30

2 Answers 2

1

My question is, how many items are there in data["response"]["docs"]? Are there exactly 11? Either way I would use the following code instead:

<% data["response"]["docs"].each_with_index do |item, index| %>
<%= index %> 
<br/>
<%= item["topic"] %> 
<% end %>

This iterates over the data["response"]["docs"] no matter how many there are (whether is is 1 doc or 20 docs) and stores the value in the variable named item. The each_with_index function gives you the index as well, stored in index, so you can display it later. If you only want the first 11 use:

<% data["response"]["docs"].first(11).each_with_index do |item, index| %>

This will grab a maximum of 11 doc items.

Sign up to request clarification or add additional context in comments.

1 Comment

It consists of hundreds of documents, but I would only like to show the first 10 for starters and this works like a charm! I didn't know you can create the loop like this, thanks!
0

It's hard to tell what might be going wrong because you haven't posted the error, but if you're using a 10-element array, you want to do:

(0..9).each do |i|

With 0-based indexes, you should only use the range from 0-9, rather than 0-10. You may be getting an error because you're trying to access an element that isn't there (i.e. at index 10).

Even better is:

<% data["response"]["docs"].each do |document| %>
<%= document["topic"] %>
<% end %>

or if you need to print the index:

<% data["response"]["docs"].each_with_index do |document, index| %>
<%= index %> <br/>
<%= document["topic"] %>
<% end %>

3 Comments

It's preferable to not use .... The 3-dot version is harder to read and is unknown to a lot of developers, leading to the possibility of bugs being injected during maintenance. It's better/idiomatic to use the 2-dot version, .. with the trailing number being reduced by 1.
Interesting, I'll start doing that instead. Thanks Tin Man. Answer has been edited.
Consider this also: It's easier to understand if you do 10.times do |i| than it is (0..9).each do |i|. i will still start at 0 and count to 9, but it's more obvious the code loops 10 times.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.