Ruby 繰り返し処理

動作環境はMacです。

#繰り返し処理#

##each##

*記述方法*

配列、ハッシュ.each do |変数|
実行したい処理　
end

配列やハッシュの中の処理が終わるまで順番に実行される。

※配列、ハッシュ名は複数形、変数名は単数形で表すことが多い。

---

**実践**

```each.rb

numbers = [1, 2, 3, 4, 5]　#変数に配列を代入

numbers.each do |number|
  puts number
end

numbers.each {|number|　#1
  puts number
}

numbers.each {|number| puts number} #2

#1と２は同じ記述を複数行で書くか一行で書くかの違い
```

出力結果

```
ruby each.rb
1
2
3
4
5

1
2
3
4
5

1
2
3
4
5
```
同じような処理を文字列を格納した配列でも実践


```each.rb
colors = ['red', 'green', 'blue']

colors.each do |color|
  puts color
end

colors.each {|color|
  puts color
```

出力結果

```
red
green
blue

red
green
blue

red
green
blue
```

##for##

*記述方法*

for 変数　in 配列やハッシュ　do 
繰り返し実行したい処理
end

---

**実践**

```for.rb

numbers = [1, 2, 3, 4 ,5]

for number in numbers do
  puts number
end

```

出力結果

```
ruby for.rb
1
2
3
4
5
```

eachとforをどちらでも使用できる場合できるだけ、eachを使用する。
forは明確な理由を説明できない限りは使わない。

The Ruby Style Guideより

**ハッシュを使用した　each**

```hash_each.eb

scores = { kevin: 98, kosugi: 60, naitou: 30}

 scores.each do |k, v| #キーと値を示す変数名
   puts v　#キーのみを出力
end
```

出力結果

```irb
ruby each_hash.rb
98
60
30
```

```hash_each.rb
 scores.each do |k, v|
   if v >= 80 #vの値が80点以上の場合のみ出力
   puts "{#{k}, #{v}}"#k,vの中身を式展開して出力
  end
end
```
出力結果

```irb

{kevin, 98} #キーの値が８０点以上のハッシュの中身が出力
```

##times##

繰り返しの処理回数が決まっている場合に便利

*記述方法*

繰り返したい回数.times do |i| 　#iは省略可能
実行したい処理
end

※変数iは省略可能

**実践**

```times.rb

5.times do
  puts 'hello'
end

5.times do |i|
  puts "{#{i}: hello}" #式展開をして、何回目の処理かわかるようにする
end

5.times { |i|
  puts "{#{i}: hello}"　#doとendを{}に置き換えても上と同じ
}
```

出力結果

```irb

hello
hello
hello
hello
hello

{0: hello} #0から始まる
{1: hello}
{2: hello}
{3: hello}
{4: hello} 

{0: hello}
{1: hello}
{2: hello}
{3: hello}
{4: hello}
```

##while##

ある一定の値で処理を止めるメソッド

**記述方法**

while 条件式　do 
実行したい処理
end

```while.rb
i = 0 #変数iの初期値を0

while i < 10 do　#iが１０未満の場合の処理
  puts i
  i += 1　#iにインクリメント処理
end
```

出力結果

```irb

0
1
2
3
4
5
6
7
8
9
```

インクリメントの処理をしないと、0が無限出力されるので注意。

##upto##

nからmまで数値を1つずつ増やしながら何かしらの処理を行いたい場合に使う。

**構文**
開始値.upto(修了値)　{実行したい処理}

**実践**

```upto.rb
10.upto(14) {|n| puts n} #変数nに値を格納し出力
```

出力結果

```irb
10
11
12
13
14
```

##downto##

nからmまで数値を1つずつ減らしながら何かしらの処理を行いたい場合に使う。

**構文**
開始値.downto(修了値)　{実行したい処理}


```upto.rb

14.downto(10) {|n| puts n}
```

出力結果

```irb 
14
13
12
11
10
```

##step##

nからmまでxずつ値を増やす(または減らす)場合に使うメソッド

例）１、３、５、７、９

**構文**

開始値.step(上限値,一度に実行したい処理){}

**実践**

```step.rb

1.step(10, 2) {|n| puts n}  #1から１０まで２ずつ増やしながら出力
```

出力結果

```irb
1
3
5
7
9
```

```step.rb

10.step(1, -2) {|n| puts n} #10から１まで2ずつ減らしながら出力

```

出力結果

```irb

10
8
6
4
2

```

##loop##

ある特定の処理を無限に繰り返したい場合に使用するメソッド

**構文**

loop do 
実行したい処理
end

**実践**

```loop.rb

i = 0

loop do
puts i
i += 1
end
```

出力結果

```irb

2624911
2624912
2624913
2624914
2624915
2624916
2624917
2624918
2624919
2624920
2624921
2624922
2624923
2624924
2624925
2624926
2624927
2624928
2624929
2624930
2624931
2624932
2624933
```

上の処理をwhileで書き換え

```loop.rb 
i = 0

while true
puts i
i += 1
end
```

出力結果

```irb
592928
592929
592930
592931
592932
592933
592934
592935
592936
592937
592938
592939
592940
592941
592942
592943
```

制御構造のbreakを使用して無限ループを抜ける

```loop.rb
i = 0

loop do
  puts i
  i += 1
  break if i == 10 #iが10になったら処理を抜ける
end
```

出力結果

```irb
0
1
2
3
4
5
6
7
8
9
```

##next##

繰り返し処理の中で、出力したい値だけを取り出すメソッド

```loop.rb

numbers = [1, 2, 3, 4, 5] #配列を変数に代入

numbers.each do |n|
  next if n % 2 == 0　　#偶数の場合は出力されない
  next if n.even? #上の処理と同じ意味
  puts n
end
```

出力結果

```irb
1
3
5
```

偶数の場合だけ出力

```loop.rb
numbers.each do |n|
  next if n.odd?
  puts n
end
```

出力結果

```irb
2
4
```