Reputation: 2467
I have a hash whose value is an array of song lyrics (line1, line2, etc..)
Code:
class Song
def initialize(lyrics)
@lyrics = lyrics
end
def get_song_name()
puts @lyrics.keys
end
def get_first_line()
puts @lyrics.values[0]
end
end
wasted = Song.new({"Wasted" => ["I like us better when we're wasted",
"It makes it easier to see"]})
real_world = Song.new("Real World" => ["Straight up what do you want to learn about here", "if i was someone else would this all fall apart"])
wasted.get_song_name()
wasted.get_first_line()
#=>I like us better when we're wasted
#=>It makes it easuer to see
So when I called wasted.get_first_line
, I want it to get the first item in the array of the value. I tried doing @lyrics.values[0]
, but it returns both lines of the song instead of the first one.
How do I accomplish this?
Upvotes: 7
Views: 8613
Reputation: 18762
This is not the answer to original question, but if I were you, I would modify the class like below. It will be more apt to store song name and lines of lyrics as individual attributes, instead of merging them as a hash - which kind of defies the whole purpose of having Song
class.
class Song
attr_accessor :song_name, :lyrics
def initialize(song_name, lyrics)
@song_name = song_name
@lyrics = lyrics
end
end
Please note that you may not need get_first_line
method. You could always use Array#first
to have same effect:
real_world = Song.new("Real World", ["Line 1", "Line 2"])
puts real_world.lyrics.first # Prints "Line 1"
You can also access lyrics lines using array index
puts real_world.lyrics[1] # Prints "Line 2"
Upvotes: 3
Reputation: 36100
Lets use this hash for example:
x = {foo: [:bar, :baz]}
x.values # => [[:bar, :baz]]
x.values.first # => [:bar, :baz]
x.values.first.first # => :bar
In other words, @lyrics.values[0]
will return the first value in the @lyrics
hash, which is the array of two songs. You still have to get the first song out of that array.
Upvotes: 3
Reputation: 16506
You need to understand that in the above code @lyrics
is a Hash. Here is what you are doing and what it translates to:
@lyrics
# => {"Wasted"=>["I like us better when we're wasted", "It makes it easier to see"]}
@lyrics.values
# => [["I like us better when we're wasted", "It makes it easier to see"]]
@lyrics.values[0]
# => ["I like us better when we're wasted", "It makes it easier to see"]
@lyrics.values[0][0]
# => "I like us better when we're wasted"
Therefore to access the first line, you need to get the first element of the values array. i.e.
@lyrics.values[0][0]
or
@lyrics.values.first.first
Upvotes: 13