🕌
RubySilver学習まとめ
現在、RubySilverの学習をしているので、ややこしい箇所をまとめていきます!
ヒアドキュメント
| 書き方 | 展開できるか? | 本文中のスペースやタブを削除する | 終了タグの前にインテンド入れられるか? |
|---|---|---|---|
<<EOT |
○ | × | × |
<<'EOT' |
×(''はエラーになる) |
× | × |
<<"EOT" |
○ | × | × |
<<~EOT |
○ | ○(自動で除去) | × |
<<~'EOT' |
×(''はエラーになる) |
○(自動で除去) | × |
<<-EOT |
○ | × | ○ (これだけエラーにならない) |
<<-'EOT' |
×(''はエラーになる) |
× | ○(これだけエラーにならない) |
展開
#{} による式展開や、バックスラッシュ記法(\n など)を使って変数・式を展開できるかどうか。
# 展開 ○
name = "Ruby"
str = <<EOT
Hello, #{name}!
EOT
# => "Hello, Ruby!"
# 展開 ×
name = "Ruby"
str = <<'EOT'
Hello, #{name}!
EOT
# => "Hello, #{name}!" # 置き換わらない
本文中のスペースやタブの自動削除
str = <<~EOT
line1
line2
EOT
# => "line1\nline2\n" # 行頭のスペースが除去される
終了ラベル(例: EOT)を、行頭からインデントして書けるかどうか

str = <<-EOT
line1
line2
EOT
# 終了ラベルの文頭にインテンド入っていてもOK
# これは動かない
def sample
<<TXT
Ruby
Java
TXT
end
p sample
終了ラベルの書き方
s = <<'EOF'
Hello,
Ruby
'EOF'
EOF
p s
# => "Hello,\nRuby\n'EOF'\n"
終了は EOF(クォートなし!)のため、'EOF'(クォート付き)は文字列内の一部になる。
短絡評価・演算子
| 演算子 | 意味 | 特徴(短絡評価) | 例 |
|---|---|---|---|
|| |
または(OR) | 左が true なら右は評価しない |
a || b => a
|
&& |
かつ(AND) | 左が false なら右は評価しない |
a && b => b
|
- |
差集合(配列演算) | 配列 a から b の要素を除外 |
[1,2,3,4] - [4,5,6] |
& |
積集合(配列演算) | 配列 a と b の共通要素を抽出 |
[1,2,3,4] & [4,5,6] |
上記表内の||部分について、半角で||と書くと表示されなくなってしまうため、わざと全角||で書いてます。
a = [1,2,3]
b = [4,5,6]
p a || b # => [1, 2, 3]
p a && b # => [4, 5, 6]
a = [1,2,3,4]
b = [4,5,6]
p a-b #=> [1, 2, 3]
p a & b #=> [4]
問題29
silver_j.mdより引用。
ary = []
ary << 1 && false
true || ary << 2
false && ary << 3
false || ary << 4
p ary
実行結果
[1, 4]
考え方
1. ary = []
空の配列を用意。
2. ary << 1 && false
評価順:
-
ary << 1は配列に1を追加し、その戻り値はary(truthy) -
truthy && false→ 結果はfalse
ary = [1]
3. true || ary << 2
評価順:
-
true || ...の時点で、||の左が真なので右は評価されない(短絡評価) -
ary << 2は実行されない!
ary = [1](そのまま)
4. false && ary << 3
評価順:
-
false && ...→ 左が偽なので右は評価されない(短絡評価) -
ary << 3実行されない!
ary = [1](変わらず)
5. false || ary << 4
評価順:
- 左が
false→ 右を評価 -
ary << 4実行 →4が配列に追加
ary = [1, 4]
6. p ary
[1, 4]
==, eql?, equal? の違い
| メソッド | 比較内容 | ゆるさ | 例 |
|---|---|---|---|
== |
値が同じか(型が違ってもOK) | ◎ ゆるい |
1 == 1.0 → true
|
eql? |
値が同じ&型も同じ | ◯ やや厳しい |
1.eql?(1.0) → false
|
equal? |
完全に同じオブジェクトか(同じID) | ✕ 厳しい |
1.equal?(1) → true、1.equal?(1.0) → false
|
-
==(等価) ← 一番ゆるい eql?(厳密な等価)-
equal?(同一性) ← 一番きびしい
a = "hello"
b = 'hello'
p a == b # => true・値が同じならOK
p a.eql?(b) # => true・値と型の両方が一致する
p a.equal?(b) # => false・同一オブジェクトか?
a = 1 # Integer
b = 1.0 # Float
p a == b # => true・値が同じならOK
p a.eql?(b) # => false・値と型の両方が一致する
p a.equal?(b) # => false・同一オブジェクトか?
a1 == a2 # => true
a1.eql? a2 # => true
-
==- 「中身(値)」が同じならtrueを返す
- 文字列の場合、"abc" == "abc" → true
-
eql?- これも「値が同じかどうか」を調べる。文字列同士で中身が同じならtrue
- 数値などでは型も比較するけど、今回はどちらもStringなので同じ
-
""(ダブルクォート)で囲んだ文字列も''(シングルクォート)で囲んだ文字列もどちらもStringクラスのインスタンス
Rubyでのハッシュ生成方法
| 書き方 | 使用可能なキー | 例 |
|---|---|---|
h = { :key => "value" } |
任意(シンボル、文字列など) | { :name => "Alice" } |
h = { key: "value" } |
シンボルのみ(Ruby 1.9以降) | { name: "Alice" } |
h = Hash.new |
空のハッシュを作る | h[:foo] = "bar" |
h = Hash[:a, 1, :b, 2] |
ペアの列で初期化 | { :a => 1, :b => 2 } |
h = Hash[ [[:a, 1], [:b, 2]] ] |
ペアの配列から作る | { :a => 1, :b => 2 } |
エイリアスメソッド
map / collect
すべての要素に対して処理を行い、変換結果を新しい配列として返す。
p [1,1,2,3,5,8].map { |x| x*2 }
# => [2,2,4,6,10,16]
[1, 2, 3].map { |n| n * 2 }
# => [2, 4, 6]
select / find_all
条件に一致する要素だけを集めて返す配列フィルタ。
[1, 2, 3, 4].select { |n| n.even? }
# => [2, 4]
reject
select の逆で、条件に一致しない要素を返す。
[1, 2, 3, 4].reject { |n| n.even? }
# => [1, 3]
find / detect
ブロックの条件を満たす最初の1つの要素を返す。
[1, 2, 3, 4].find { |n| n.even? }
# => 2
Discussion