一緒にRubyを征服します! ドロップ10

このドロップでは、再びOOPに深く入り、クラス、オブジェクト、モジュールを操作する新しい方法を見つけ出します。これらは、本格的なプログラミングで役立つでしょう。

複数のコンストラクター


オブジェクトに対して複数のコンストラクターが必要な場合はどうなりますか? 新しいオブジェクトを返す追加のクラスメソッドの作成を妨げるものは何もありません。 次の例では、体重、身長、色ごとに3つの5つのパラメーターを持つ猫について説明します。 「デフォルトで」いくつかのタイプの猫を定義する追加のメソッドを作成します(たとえば、黒猫や太った猫)。

class SuperCat

def initialize ( height, weight, tail_color, head_color, legs_color )
@height , @weight , @tail_color , @head_color , @legs_color = height, weight, tail_color, head_color, legs_color
end

def
SuperCat . white_cat ( height, weight )
new ( height, weight, "white" , "white" , "white" )
end

def
SuperCat . black_cat ( height, weight )
new ( height, weight, "black" , "black" , "black" )
end

def
SuperCat . big_cat ( tail_color, head_color, legs_color )
new ( 100, 100, tail_color, head_color, legs_color )
end

end
a = SuperCat . new ( 10, 15, "white" , "black" , "white" )
b = SuperCat . black_cat ( 13, 20 )
c = SuperCat . big_cat ( "white" , "red" , "red" )
p ( a ) ; p ( b ) ; p ( c )


ここに「コンストラクター」という言葉がありますか? この質問は弁護士にお任せします:)

コンストラクター開発


オブジェクトはより複雑になり、オブジェクトを作成するときに初期化する必要がある属性をますます収集しています。 このコンストラクトの責任は長くて面倒になり、パラメータの再集計と行の折り返しが必要になります。

この複雑さに対処する1つの方法は、 ブロックinitializeメソッドに渡すことです。 次に、ブロックを使用してオブジェクトを初期化できます。 eval:代わりにinstance_evalメソッドを使用しinstance_eval eval:
class HyperCat
attr_accessor :name ,
:height , :weight , :age ,
:tail_color , :head_color , :legs_color

def initialize ( &block )
instance_eval &block
end

# ...
end

pussy = HyperCat . new do
self
. name = "Pussy"
self . height = 10
self . weight = 12
self . age = 3.2
self . tail_color = "gray"
self . head_color = "gray"
self . legs_color = "white"
end

p pussy

属性でアクセサーを使用するため、値をより簡単に渡すことができます。 また、値の割り当て方法は常に明示的なレシーバーを使用してローカル変数を作成するため、 self参照する必要があります。

メソッドアクセス制御


Rubyでは、オブジェクトは主に、提供するインターフェイス、他のユーザーが利用できるようになるメソッドによって決定されます。 ただし、クラスを記述する場合、クラス内で使用される補助メソッドが必要になることがよくありますが、外部からアクセスできる場合は危険です。 これは、 Moduleクラスのprivateメソッドが役立つ場所です。

private 2つの方法で使用できます。 クラスの本体でパラメーターなしでprivateを呼び出すと、以下のすべてのメソッドがprivateになります。 または、メソッドのリストをprivateパラメータとして文字として渡すことができます。
class Bank
def open_safe
# ...
end

def
close_safe
# ...
end

private :open_safe , :close_safe

def make_withdrawal ( amount )
if access_allowed
open_safe
get_cash ( amount )
close_safe
end
end

# -

private

def get_cash
# ...
end

def
access_allowed
# ...
end
end


オブジェクトをコピーする


dupメソッドとdupメソッドは、呼び出し元のコピーを作成します。 dupメソッドはオブジェクトのコンテンツのみをコピーしますが、 cloneはオブジェクトに関連付けられたシングルトンクラスのようなものを取ります。
s1 = "cat"

def s1 . upcase
"CaT"
end

s1_dup = s1. dup
s1_clone = s1. clone
s1 #=> "cat"
s1_dup. upcase #=> "CAT" ( )
s1_clone. upcase #=> "CaT"


モジュールの詳細


一滴戻して、特にモジュールとその使用方法を思い出してください。特に、不純物とそこに示されている例に注意してください。
しかし、モジュールメソッドと混合するとどうなりますか? クラスメソッドとして含まれると思われる場合、Rubyは含まれません。 これを行うには、これを行うことができます:
module MyMod

def meth
puts " "
puts " ."
end

end

class
MyClass

class << self # self MyClass
include MyMod
end

end

ここで、 extendメソッドは便利です。これにより、例がはるかに簡単になります。
class MyClass
extend MyMod
end
MyClass . meth


構造体の作成


場合によっては、さらに処理せずに一部のデータをグループ化するだけで済みます。 クラスを作成できます:
class ExtraCat

attr_accessor :name , :age , :weight

def initialize ( name, age, weight )
@name , @age , @weight = name, age, weight
end

end

lucky = ExtraCat . new ( "Lucky" , 2, 4 )
これはもちろん機能しますが、繰り返しのみがあります。 そのため、 StructクラスがStructました。 attr_accessorが必要なメソッドを定義するように、 Structは同じ属性を含むクラスを定義します。 これらのクラスは構造テンプレートと呼ばれます。
ExtraCat = Struct . new ( "ExtraCat" , :name , :age , :weight )
lucky = ExtraCat . new ( "Lucky" , 2, 4 )

エピローグ


一般に、私は勉強のためにトピックを採点したので、レールは再び行きます(敷設されますか?)森のそばで:)ちょっと待ってください。しかし、それは必要です。 はい、そして最後に、コードの強調表示を作成しました、私がしなければならなかったのは、Windows Live Writer + Visual Studio + VSPaste + HTML Snippet + PowerGREP +正規表現+ペンでのいくつかの作業だけでしたことがわかりました:私はもう記事を失うことを恐れていません;)そして、もちろん、シリーズのすべての記事はStartup Programmerブログであなたを待っています

Source: https://habr.com/ru/post/J49418/


All Articles