search
LoginSignup
0
Help us understand the problem. What are the problem?

posted at

【Ruby】ハッシュとシンボルについて学んだこと

はじめに

チェリー本を読んで、ハッシュとシンボルについて学んだので簡単にまとめました!

参考

プロを目指す人のためのRuby入門 言語仕様からテスト駆動開発・デバッグ技法まで

ハッシュとは

キーと値の組み合わせでデータを管理するオブジェクトのこと

ハッシュの書き方

キーが文字列かシンボルによって、書き方が変わります。

キーをシンボルにする場合(一般的)

{キー:値}でハッシュを生成します。

キーをシンボルにした場合のハッシュの書き方
profile = {name:'太郎'}

キーを文字列にする場合

{キー=>値}でハッシュを生成します。
ただし、あまり一般的な方法ではないようです。

キーを文字列にした場合のハッシュの書き方
profile = {'name' => '太郎'}

要素の追加・変更

追加・変更ともに、「ハッシュ[キー] = 値」で記述します。
上記で指定したキーが、

  • 存在しない場合は:追加
  • 存在する場合は:変更
    と、挙動が変わります。
要素の追加
profile = {名前:'太郎'}

# 追加
profile[:] = '田中'
p profile #=>{:名前=>"太郎", :姓=>"田中"}

# 変更
profile[:] = '佐藤'
p profile #=>{:名前=>"太郎", :姓=>"田中"}

値の取得

ハッシュ[:シンボル名]で値を取得します。

キーをシンボルにした場合の値の取得方法
profile = {name:'太郎'}
p profile[:name] #=>"太郎"

要素の削除

「ハッシュ.delete(キー)」で削除ができます。

要素の削除
profile = {
    name:'太郎',
    family_name:'佐藤',
}
profile.delete(:family_name)
p profile #=>{:name=>"太郎"}

ハッシュを使った繰り返し

ブロックパラメーターを2つ用意することで、キーと値がブロックに渡されます。

ハッシュを使った繰り返し
members = {
    1=>"太郎",
    2=>"佐藤",
    3=>"次郎",
}

members.each do |num,name|
    puts "#{num}番は#{name}です"
end

#=>1番は太郎です
# 2番は佐藤です
# 3番は次郎です

シンボルと文字列の違い

比較対象とされるシンボルと文字列ですが、下記のような違いがあります。

①オブジェクトが一緒か異なるかの違い

例えば下記のコードのように、「太郎」という文字を,

  • シンボルで3つ生成した場合:3つともobuject_idが一緒
  • 文字列で3つ生成した場合:3つともobuject_idが異なる
    という違いがあります。
    つまり、シンボルと文字列では、同じ文字でも生成されるオブジェクトの数が変わります。
    文字列のように、オブジェクトが生成されればされるほど、占有するメモリも増えてしまうため、同じ用途なのであれば、シンボルを使用した方が、メモリの使用効率が良くなります!
シンボルと文字列のobject_idの違い
#シンボルの場合、object_idが一緒
p :太郎.object_id #=> 1056668
p :太郎.object_id #=> 1056668
p :太郎.object_id #=> 1056668

#文字列の場合、object_idが異なる
p '太郎'.object_id #=>70212967994280
p '太郎'.object_id #=>70212967994200
p '太郎'.object_id #=>70212967994120

②ミュータブルかイミュータブルの違い

  • 文字列はミュータブル(値の変更が可能)ですが、
  • シンボルはイミュータブル(値の変更が不可)になります。
    そのため、名前やIDなどのように、「一度定めたら変えることがない」ケースにシンボルが使われます。
ミュータブルかイミュータブルの違い
#文字列の場合、値の変更が可能(ミュータブル)
name = 'taro'
p name.upcase! #=>"TARO"

#シンボルの場合、値の変更が不可(イミュータブル)
name = :taro
p name.upcase! #=>NoMethodError

シンボルの特徴

シンボルの特徴は、

  1. ソースコード上は、文字列に見えるため人が識別しやすい
  2. 一方、内部的には整数のため、文字列を比較するよりも処理が早い
  3. 同じシンボルは同じオブジェクトのため、メモリの使用効率が文字列を使うより高い
  4. イミュータブルなので、破壊的メソッド防止になる(勝手に値が変わる心配がない)

ハッシュの展開

**をハッシュの前につけることで、ハッシュの中身が展開されます。

ハッシュ展開の例
a = { depth:1 }
size = {
    width:2,
    height:3,
    **a
}
p size #=>{:width=>2, :height=>3, :depth=>1}

シンボルを文字列に変換する方法

to_symメソッドを使用します。

'name'.to_sym #=>:name

まとめ

ハッシュのキーに文字列ではなく、シンボルを使う理由は勉強になりました!
間違いやアドバイスがあればご教授いただけますと幸いです。

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
What you can do with signing up
0
Help us understand the problem. What are the problem?