8. ProgateでRubyⅠ~Ⅴ(備忘録)

Ruby 学習コースⅠ(基本的な文法)

・Rubyの実行

# index.rb
puts "Hello World"
puts 6 / 2
puts 9 % 2

(出力結果)

Hello World
3
1

・変数の定義

# index.rb
name = "John"
puts name

(出力結果)

John

・自分自身に代入する

# index.rb
a = 2
a = a + 3

# 下記のように省略可能
x += 10		# x = x + 10
x -= 10		# x = x - 10
x *= 10		# x = x * 10
x /= 10		# x = x / 10
x %= 10		# x = x % 10

・変数展開

name = "佐藤"
puts "こんにちは#{name}さん"		# シングルクォーテーションの場合は変数展開されないので注意

age = 19
puts "#{age}歳です"				# 変数展開を用いると、数値と文字列の連結も可能

(出力結果)

こんにちは佐藤さん
19歳です

・条件分岐

score = 94
if score > 80
	puts "よくできました"
elsif score > 60
	puts "まずまずです"
else
	puts "もっと頑張りましょう"
end

(出力結果)

よくできました

・比較演算子

a == b		# aとbが等しいときtrue
a != b		# aとbが異なる時true

・複数の条件の組み合わせ

条件1 && 条件2		# 条件1かつ条件2(複数の条件がすべてtrueならtrue)
条件1 || 条件2		# 条件1または条件2(複数の条件のうち一つでもtrueならtrue)

・完成版

# index.rb
year = 2000				# 好きな年を西暦で代入

if year < 1896
  puts "#{year}年にオリンピックはまだありません"
elsif year == 1916 || year == 1940 || year == 1944
  puts "#{year}年にオリンピックは開催されませんでした"
elsif year % 4 == 0
  puts "#{year}年は夏季オリンピックが開催されました"
else 
  puts "#{year}年は夏季オリンピックイヤーではありません"
end

(出力結果)

2000年は夏季オリンピックが開催されました

Ruby 学習コースⅡ(配列/繰り返し処理/ハッシュ)

・配列

# index.rb
names = ["Suzuki", "Kato", "Tanaka"]
puts names
puts names[1]		# インデックス番号1の値だけが出力される

(出力結果)

Suzuki
Kato
Tanaka
Kato				# インデックス番号1の値

・each文を使った繰り返し処理

# index.rb
names = ["Suzuki", "Kato", "Tanaka"]

names.each do |name|
	puts "名前は #{name} です"
end

(出力結果)

名前は Suzuki です
名前は Kato です
名前は Tanaka です

・ハッシュ

# index.rb
user = {"name" => "Suzuki", "age" => 21}
puts user["name"]

user["age"] = 22			# キー"age"に対応する値を22に更新
puts user["age"]

user["gender"] = "male"		# キー"gender"に対応する値を追加
puts user

(出力結果)

Suzuki
22
{"name" => "Suzuki", "age" => 22, "gender" => "male"}		# "gender"要素が追加されている

・ハッシュのキーにシンボルを用いる

# index.rb
user = {"name" => "Suzuki", "age" => 21}
user = {:name => "Suzuki", :age => 21}		# 先頭にコロンを付けた「シンボル」という書き方もできる
puts user[:name]

(出力結果)

Suzuki

・キーがシンボルの場合のハッシュの省略

# index.rb
{:name => "Suzuki", :age => 21}
{name: "Suzuki", age: 21}			# 「:key =>」を「key:」に省略可能
puts user[:name]					# 省略した書き方の場合でも、シンボルを用いて要素を取得する

(出力結果)

Suzuki

・ハッシュの書き方まとめ

# index.rb
# キーが文字列の書き方
{"name" => "Suzuki", "age" => 21}
# キーがシンボルの書き方
{:name => "Suzuki", :age => 21}
# キーがシンボルの書き方(省略形)
{name: "Suzuki", age: 21}

・配列の要素にハッシュを入れる

# index.rb
users = [
	{name: "Suzuki", age: 21},
	{name: "Kato", age: 14}
]
puts users[1]
puts users[1][:name]

(出力結果)

{:name => "Kato", :age => 14}
Kato

・each文の中でハッシュの値を使う

# index.rb
users = [
	{name: "Suzuki", age: 21},
	{name: "Kato", age: 14}
]

users.each do |user|
	puts user[:name]
end

(出力結果)

Suzuki
Kato

・完成版

# index.rb
olympics = [
  {year: 1896, city: "アテネ"},
  {year: 1900, city: "パリ"},
  {year: 1904, city: "セントルイス", note: "アメリカ初開催"},
  {year: 1908, city: "ロンドン"},
  {year: 1912, city: "ストックホルム"},
  {year: 1916, city: "ベルリン", note: "第一次世界大戦で中止"},
  {year: 1920, city: "アントワープ"},
  {year: 1924, city: "パリ", note: "同じ都市での2回目の開催は初"},
  {year: 1928, city: "アムステルダム"},
  {year: 1932, city: "ロサンゼルス"}
]

puts "第1~10回大会のオリンピック一覧"

olympics.each do |olympic|
  puts "---------------------"
  puts "#{olympic[:year]}年#{olympic[:city]}大会"
  
  if olympic[:note] != nil
    puts "豆知識: #{olympic[:note]}"
  end
end

(出力結果)

第1~10回大会のオリンピック一覧
---------------------
1896年アテネ
---------------------
1900年パリ
---------------------
1904年セントルイス
豆知識: アメリカ初開催
---------------------
1908年ロンドン
---------------------
1912年ストックホルム
---------------------
1916年ベルリン
豆知識: 第一次世界大戦で中止
---------------------
1920年アントワープ
---------------------
1924年パリ
豆知識: 同じ都市での2回目の開催は初
---------------------
1928年アムステルダム
---------------------
1932年ロサンゼルス

Ruby 学習コースⅢ(メソッド)

・メソッドの定義

# index.rb
def introduce					# メソッド名
	puts "こんにちは"
	puts "私はにんじゃわんこです"
end
introduce

(出力結果)

こんにちは
私はにんじゃわんこです

・メソッド内で引数を使用する

# index.rb
def introduce(name)				# name引数に値が代入される
	puts "こんにちは"
	puts "私は#{name}です"
end
introduce("にんじゃわんこ")		# この値が引数として代入される
introduce("ひつじ仙人")

(出力結果)

こんにちは
私はにんじゃわんこです
こんにちは
私はひつじ仙人です

・複数の引数を受け取る

# index.rb
def introduce(name, age)
	puts "私は#{name}です"
	puts "#{age}歳です"
end
introduce("にんじゃわんこ", 14)

(出力結果)

私はにんじゃわんこです
14歳です

・戻り値を受け取る

# index.rb
def add(a,b)
	return a + b
end
sum = add(1,3)
puts sum

(出力結果)

4

・真偽値を返すメソッド

# index.rb
def negative?(number)
	return number < 0
end
puts negative?(5)

(出力結果)

false

・キーワード引数を用いた書き方

# index.rb
def introduce(name:, age:, food:)
	puts "私は#{name}です"
	puts "年齢は#{age}です"
	puts "好きな食べ物は#{food}です"
end
introdece(name: "にんじゃわんこ", age: 14, food: "ラーメン")

(出力結果)

私はにんじゃわんこです
年齢は14歳です
寿司な食べ物はラーメンです

・完成版

# index.rb
def buy(item:, price:, count:)					# キーワード引数を使用
	puts "#{item}を#{count}台のお買い上げです"
	puts "合計金額は#{price * count}円です"
end

buy(item: "テレビ", price: 15000, count: 2)	# キーワード引数を使用

(出力結果)

テレビを2台のお買い上げです
合計金額は30000円です

Ruby 学習コースⅣ(クラス)

・クラスの定義

# index.rb
class Menu					# クラスを定義
	attr_accessor :name		# インスタンス変数
	attr_accessor :price
end

・インスタンスの生成

# index.rb
class Menu
	attr_accessor :name
	attr_accessor :price
end
menu1 = Menu.new			# Menuクラスからインスタンスを生成
menu1.name = "すし"			# インスタンス変数に値を代入する
puts menu1.name

(出力結果)
すし

・クラス内でメソッドを定義する

# index.rb
class Menu
	attr_accessor :name
	attr_accessor :price

	def show				# クラスの中でメソッドを定義
		puts "私はメニューです"
	end
end

menu1 = Menu.new
menu1.show				# クラスの中で定義したインスタンスに対してメソッドを呼び出す(インスタンスメソッド)

(出力結果)

私はメニューです

・インスタンスメソッドで引数を受け取ったり戻り値を返す

# index.rb
class Menu
	:
	def show(data)
		return "私は#{data}です"
	end
end
menu1 = Menu.new
puts menu1.show("メニュー")

(出力結果)

私はメニューです

・インスタンスメソッドで引数を受け取ったり戻り値を返す

# index.rb
class Menu
	:
	def show_name
		puts "私は#{self.name}です"		# 特殊な変数「self」には、呼び出したインスタンス自身が代入される
	end
end
menu1 = Menu.new
menu1.name = "ピザ"
menu1.show_name			# インスタンスメソッドの呼び出し

(出力結果)

私はピザです

・合計金額を求めるメソッド

# index.rb
class Menu
	:
	def get_total_price(count)
		total_price = self.price * count
		if count >= 3
			return total_price - 100
		end
		return total_price
	end
end

menu1 = Menu.new
menu1.name = "ピザ"
menu1.price = 800

puts menu1.get_total_price(3)

(出力結果)

2300

・インスタンス生成時に値を代入する

# index.rb
class Menu
	:
	def initialize
		puts "メニューが生成されました"
	end
	:
end
menu1 = Menu.new		# Menu.newが実行されると自動でinitializeメソッドが呼び出される

(出力結果)

メニューが生成されました

・initializeメソッドに引数を渡す

# index.rb
class Menu
	:
	def initialize(message)
		puts message
	end
	:
end
menu1 = Menu.new("こんにちは")		# initializeメソッドに値を渡すことができる

(出力結果)

こんにちは

・initializeメソッドに引数を渡す②

# index.rb
class Menu
	:
	def initialize(name:, price:)
		self.name = name
		self.price = price
	end
	:
end
menu1 = Menu.new(name: "ピザ", price: 800)

・ファイルを分割する

# index.rb
require "./menu"		# menu.rbの読み込み

menu1 = Menu.new(name: "ピザ", ・・・)

# menu.rb
class Menu
	attr_accessor :name
	attr_accessor :price
	:
end

・インスタンスの配列

# index.rb
menu1 = Menu.new(name: "ピザ", price: 800)
menu2 = Menu.new(name: "すし", price: 1000)
	:
menus = [menu1, menu2, ・・・]

menus.each do |menu|
	puts menu.info
end

(出力結果)

ピザ 800円
すし 1000円
	:

・繰り返し処理で番号を付ける

# index.rb
fruits = ["apple", "banana", "orange"]
index = 0
fruits.each do |fruit|
	puts "#{index}. #{fruit}"
	index += 1
end

(出力結果)

0. apple
1. banana
2. orange

・コンソールから入力を受け取る

# index.rb
puts "名前を入力してください"
name = gets.chomp					# コンソールから入力された値を変数へ代入
puts "あなたの名前は#{name}です"

(出力結果)

名前を入力してください
Suzuki								# コンソール上から入力
あなたの名前はSuzukiです

・数値を受け取る

# index.rb
puts "数字を入力してください"
number = gets.chomp.to_i			# 入力された内容を数値に変換
puts "#{number}の2倍は#{number * 2}です"

(出力結果)

数字を入力してください
3									# コンソール上から入力
3の2倍は6です

・完成版

# index.rb
require "./menu"

menu1 = Menu.new(name: "ピザ", price: 800)
menu2 = Menu.new(name: "すし", price: 1000)
menu3 = Menu.new(name: "コーラ", price: 300)
menu4 = Menu.new(name: "お茶", price: 200)

menus = [menu1, menu2, menu3, menu4]

index = 0
menus.each do |menu|
	puts "#{index}. #{menu.info}"
	index += 1
end

puts "--------------"
puts "メニューの番号を選択してください"

# 入力を数値として受け取って変数orderに代入する
order = gets.chomp.to_i

# 選択されたメニューのインスタンスを変数selected_menuに代入する
selected_menu = menus[order]

# 「選択されたメニュー: ○○」となるように出力
puts "選択されたメニュー: #{selected_menu.name}"

puts "個数を入力してください(3つ以上で100円割引)"

# 入力を数値として受け取って変数countに代入する
count = gets.chomp.to_i

# 「お会計は○○円です」となるように出力
puts "お会計は#{selected_menu.get_total_price(count)}円です"
# menu.rb
class Menu
  attr_accessor :name
  attr_accessor :price
  
  def initialize(name:, price:)
    self.name = name
    self.price = price
  end
  
  def info
    return "#{self.name} #{self.price}円"
  end
  
  def get_total_price(count)
    total_price = self.price * count
    if count >= 3
      total_price -= 100
    end
    return total_price
  end
end

(出力結果)

0. ピザ 800円
1. すし 1000円
2. コーラ 300円
3. お茶 200円
--------------
メニューの番号を選択してください
1								# メニューを選択
選択されたメニュー: すし
個数を入力してください(3つ以上で100円割引)
3								# 個数を入力
お会計は2900円です

Ruby 学習コースⅤ(クラスの継承)

・クラスの継承
クラスを継承すると、インスタンス変数とインスタンスメソッドが引き継がれます。

# food.rb
require ".menu"

class Food < Menu		# Menuクラス(親クラス)をFoodクラス(子クラス)が継承できる
end

・子クラスのインスタンス

# index.rb
food1 = Food.new(name: "ピザ", price: 800)		# FoodクラスはMenuクラスを継承している
puts food1.name			# インスタンス変数
puts food1.info			# インスタンスメソッド

・子クラスにインスタンス変数を追加

# food.rb
class Food < Menu
	attr_accessor :calorie		# Foodクラスに「calorie」を追加
end

・子クラスにインスタンスメソッドを追加

# food.rb
class Food < Menu
	attr_accessor :calorie

	def calorie_info
		return "#{self.name}は#{self.calorie}kcalです"
	end
end

・オーバーライド
親クラスにあるメソッドと同じ名前のメソッドを子クラスで定義すると、メソッドを上書きすることができます。

# index.rb
food1 = Food.new(・・・)
food1.calorie = 700
puts food1.info

# food.rb
class Foold < Menu
	:
	def info			# メソッドの上書き(子クラスで定義したメソッドを優先して呼び出す)
		return "#{self.name} #{self.price}円 (#{self.calorie}kcal)"
	end
end

・メソッド内の重複をまとめる
オーバーライドしたメソッドの中で「super」とすることで、親クラスの同名のメソッドを呼び出すことができます。

# menu.rb
class Menu
	attr_accessor :name
	attr_accessor :price

	def initialize(name:, price:)
		self.name = name
		self.price = price
	end
	:
end
# food.rb
class Food < Menu
	attr_accessor :calorie

	def initialize(name:, price:, calorie:)
		super(name: name, price: price)		# 親クラスの同名のメソッドを呼び出し
		self.calorie = calorie
	end
	:
end

・Dateクラスの読み込み

# index.rb
require "date"			# Rubyがすでに用意しているクラスは、記述が少し異なる(./dateではない)

date1 = Date.new(2014, 7, 31)		# インスタンスを生成
puts date1
puts date1.sunday?		# Dateクラスには多くのインスタンスメソッドが用意されている

date2 = Date.today		# 今日の日付のインスタンスを生成(クラスメソッド)
puts date1

(出力結果)
2014-07-31
false
2018-12-08

・クラスメソッドの定義

# menu.rb
class Menu
	:
	def Menu.is_discount_day?		# 「def クラス名.メソッド名」でクラスメソッドを定義する
		# 処理
	end
end
puts Menu.is_discount_day?

・インスタンスメソッドとクラスメソッド

# menu.rb
class Menu
	def info
	end
end
menu1 = Menu.new
menu1.info		 # インスタンスメソッドは、インスタンスに対して呼び出す
# menu.rb
class Menu
	def Menu.is_discount_day?
	end
end
Menu.is_discount_day?		# クラスメソッドは、クラスに対して呼び出す

・完成版

# menu.rb
require "date"		# Rubyがすでに用意しているクラスは、記述が少し異なる

class Menu
  attr_accessor :name
  attr_accessor :price

  def initialize(name:, price:)
    self.name = name
    self.price = price
  end
  
  def info
    return "#{self.name} #{self.price}円"
  end
  
  def get_total_price(count)
    total_price = self.price * count
    if count >= 3
      total_price -= 100
    end
    
    if count >= 1 && Menu.is_discount_day?		# 日曜日は100円引き
      total_price -= 100
    end
    
    return total_price
  end
  
  def Menu.is_discount_day?		# クラスメソッドを定義
    today = Date.today		# 今日の日付のインスタンスを生成(クラスメソッド)
    return today.sunday?		# 日曜かどうか判定
  end
end
# food.rb
require "./menu"

class Food < Menu
  attr_accessor :calorie
  
  def initialize(name:, price:, calorie:)
    super(name: name, price: price)		# 親クラスの同名のメソッドを呼び出し
    self.calorie = calorie
  end
  
  def info
    return "#{self.name} #{self.price}円 (#{self.calorie}kcal)"
  end
  
  def calorie_info
    return "#{self.name}は#{self.calorie}kcalです"
  end
end
# drink.rb
require "./menu"

class Drink < Menu
  attr_accessor :amount
  
  def initialize(name:, price:, amount:)
    super(name: name, price: price)		# 親クラスの同名のメソッドを呼び出し
    self.amount = amount
  end
  
  def info
    return "#{self.name} #{self.price}円 (#{self.amount}mL)"
  end
end
# index.rb
require "./food"
require "./drink"

puts "日曜限定100円割引セール実施中!"

food1 = Food.new(name: "ピザ", price: 800, calorie: 700)
food2 = Food.new(name: "すし", price: 1000, calorie: 600)
drink1 = Drink.new(name: "コーラ", price: 300, amount: 500)
drink2 = Drink.new(name: "お茶", price: 200, amount: 400)

menus = [food1, food2, drink1, drink2]

index = 0
menus.each do |menu|
  puts "#{index}. #{menu.info}"
  index += 1
end

puts "--------------"
puts "メニューの番号を選択してください"
order = gets.chomp.to_i

selected_menu = menus[order]
puts "選択されたメニュー: #{selected_menu.name}"

puts "個数を入力してください(3つ以上で100円割引)"
count = gets.chomp.to_i

puts "お会計は#{selected_menu.get_total_price(count)}円です"

(出力結果)

日曜限定100円割引セール実施中!
0. ピザ 800円
1. すし 1000円
2. コーラ 300円
3. お茶 200円
--------------
メニューの番号を選択してください
1                               # メニューを選択
選択されたメニュー: すし
個数を入力してください(3つ以上で100円割引)
3                               # 個数を入力
お会計は2900円です                 # もし日曜なら100円割引される