Latest web development tutorials

Ruby berorientasi objek

Ruby adalah bahasa berorientasi objek murni, ruby, semuanya dalam bentuk benda. Setiap nilai di Ruby adalah obyek, bahkan hal yang paling primitif: string, angka, dan bahkan benar dan salah adalah obyek. Kelas itu sendiri adalahobyek yangmerupakan instancedarikelaskelas.Bab ini menjelaskan semua fungsi utama yang terkait dengan Ruby berorientasi objek.

Kelas digunakan untuk membentuk objek tertentu, yang menggabungkan representasi data dan metode untuk mengatur data ke dalam paket rapi. Kelas data dan metode yang disebut anggota kelas.

definisi kelas ruby

Ketika Anda mendefinisikan kelas, Anda benar-benar menentukan cetak biru untuk tipe data. Ini benar-benar tidak mendefinisikan data, tetapi definisi apa nama sarana kelas, yang mengatakan, definisi apa yang merupakan obyek dari kelas akan, dan tindakan apa yang dapat dilakukan pada objek.

definisi kelas dimulai dengankelas kata kunci,diikuti dengannama kelas,dan akhirnyaberakhirdengan representasi terpisah membatasi definisi tersebut. Sebagai contoh, kita menggunakan kata kunci class untuk mendefinisikan kelas Box, sebagai berikut:

class Box
   code
end

Dengan konvensi, nama harus dimulai dengan huruf besar, jika mengandung lebih dari satu kata, memanfaatkan huruf pertama dari setiap kata, tapi di sini ada pembatas (misalnya: CamelCase).

definisi objek Ruby

Kelas menyediakan cetak biru untuk sebuah objek, jadi pada dasarnya, objek dibuat sesuai dengan kelas. Kami menggunakan kata kuncibaru untuk menyatakan objek kelas.Pernyataan berikut mendeklarasikan kelas Box dua benda:

box1 = Box.new
box2 = Box.new

menginisialisasi metode

Metodemenginisialisasi adalah metode kelas Ruby standar konstruktor dari kelas, mirip dengan bahasa pemrograman berorientasi objek karya konstruktorlainnya. Bila Anda ingin menginisialisasi beberapa variabel di kelas untuk membuat obyek pada saat yang sama, menginisialisasi metode berguna. Metode ini mengambil serangkaian argumen, seperti metode Ruby lain, menggunakan metode ini, harus ditempatkan di depankata kunci def,sebagai berikut:

class Box
   def initialize(w,h)
      @width, @height = w, h
   end
end

variabel instan

kelas propertimisalnya variabel adalah bahwa mereka menciptakan saat menggunakan objek kelas akan menjadi milik objek.sifat individu masing-masing objek ditugaskan antara benda-benda lain, dan tidak berbagi nilai-nilai. Dalam kelas adalah dengan menggunakan operator @ untuk mengakses properti-properti di luar kelas, itu adalahumum untuk menggunakan metode yang disebut metode accessorakses. Di sini kita mendefinisikanBox kelas atas sebagai contoh, kelas Box @width dan @height sebagai variabel instance.

class Box
   def initialize(w,h)
      # 给实例变量赋值
      @width, @height = w, h
   end
end

Accesor (accessor) & setter metode (setter)

Untuk menggunakan variabel eksternal kelas, kita harus mendefinisikan variabel-variabel ini dalammetode akses internal,accessor adalah setaragetter.Contoh berikut menunjukkan metode accessor:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造函数
   def initialize(w,h)
      @width, @height = w, h
   end

   # 访问器方法
   def printWidth
      @width
   end

   def printHeight
      @height
   end
end

# 创建对象
box = Box.new(10, 20)

# 使用访问器方法
x = box.printWidth()
y = box.printHeight()

puts "Width of the box is : #{x}"
puts "Height of the box is : #{y}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Width of the box is : 10
Height of the box is : 20

Serupa dengan metode akses yang digunakan untuk mengakses nilai variabel, Ruby menyediakan cara untuk menetapkan nilai eksternal variabel kelas A, juga dikenal sebagaimetode setter, didefinisikan sebagai berikut:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end

   # 访问器方法
   def getWidth
      @width
   end
   def getHeight
      @height
   end

   # 设置器方法
   def setWidth=(value)
      @width = value
   end
   def setHeight=(value)
      @height = value
   end
end

# 创建对象
box = Box.new(10, 20)

# 使用设置器方法
box.setWidth = 30
box.setHeight = 50

# 使用访问器方法
x = box.getWidth()
y = box.getHeight()

puts "Width of the box is : #{x}"
puts "Height of the box is : #{y}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Width of the box is : 30
Height of the box is : 50

Metode instance

Mendefinisikanmetode instan dan metode lain yang ditetapkan, mereka menggunakan kata kunci def,tapi mereka hanya dapat digunakan oleh instance kelas, seperti yang ditunjukkan dalam contoh berikut. Fungsi mereka tidak terbatas untuk mengakses variabel instan, tetapi juga sesuai dengan kebutuhan Anda untuk melakukan tugas-tugas lain yang lebih.

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造方法
   def initialize(w,h)
      @width, @height = w, h
   end
   # 实例方法
   def getArea
      @width * @height
   end
end

# 创建对象
box = Box.new(10, 20)

# 调用实例方法
a = box.getArea()
puts "Area of the box is : #{a}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Area of the box is : 200

metode kelas variabel kelas &

variabel kelas adalah semua contoh dari variabel kelas bersama.Dengan kata lain, variabel instance kelas dapat diakses semua contoh objek. variabel kelas dengan dua @ karakter (@@) sebagai awalan, variabel kelas harus diinisialisasi dalam definisi kelas, seperti yang ditunjukkan dalam contoh berikut.

metode kelas def self.methodname ()definisi, metode kelas untuk mengakhiri pembatas. metode kelas dapat digunakan dengan bentuk nama kelasclassname.methodname panggilan, seperti yang ditunjukkan dalam contoh berikut:

#!/usr/bin/ruby -w

class Box
   # 初始化类变量
   @@count = 0
   def initialize(w,h)
      # 给实例变量赋值
      @width, @height = w, h

      @@count += 1
   end

   def self.printCount()
      puts "Box count is : #@@count"
   end
end

# 创建两个对象
box1 = Box.new(10, 20)
box2 = Box.new(30, 100)

# 调用类方法来输出盒子计数
Box.printCount()

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Box count is : 2

metode to_s

Setiap kelas memiliki metode contohto_s yang Anda tetapkan untuk kembali representasi string objek.Berikut ini adalah contoh sederhana, sesuai dengan lebar dan tinggi mewakili Box benda:

#!/usr/bin/ruby -w

class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end
   # 定义 to_s 方法
   def to_s
      "(w:#@width,h:#@height)"  # 对象的字符串格式
   end
end

# 创建对象
box = Box.new(10, 20)

# 自动调用 to_s 方法
puts "String representation of box is : #{box}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

String representation of box is : (w:10,h:20)

Access Control

Ruby menyediakan Anda dengan tiga tingkat metode instan perlindungan, yangpublik, swasta atau dilindungi.Aplikasi kontrol akses tidak di Ruby contoh dan kelas variabel.

  • Metode umum: metode umumdapat disebut benda. Secara default, metode yang umum, kecuali untuk metode initialize selalu swasta.
  • Metode pribadi: metode pribaditidak dapat diakses atau dilihat dari luar kelas. metode kelas hanya dapat mengakses anggota pribadi.
  • Metode dilindungi: dilindungi metode hanya dapat disebut kelas objek dan subclass.Akses hanya dapat dilakukan di kelas internal dan subclass.

Berikut ini adalah contoh sederhana yang menunjukkan sintaks tiga modifier:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end

   # 实例方法默认是 public 的
   def getArea
      getWidth() * getHeight
   end

   # 定义 private 的访问器方法
   def getWidth
      @width
   end
   def getHeight
      @height
   end
   # make them private
   private :getWidth, :getHeight

   # 用于输出面积的实例方法
   def printArea
      @area = getWidth() * getHeight
      puts "Big box area is : #@area"
   end
   # 让实例方法是 protected 的
   protected :printArea
end

# 创建对象
box = Box.new(10, 20)

# 调用实例方法
a = box.getArea()
puts "Area of the box is : #{a}"

# 尝试调用 protected 的实例方法
box.printArea()

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut. Di sini, metode panggilan pertama berhasil, tetapi metode kedua akan memiliki masalah.

Area of the box is : 200
test.rb:42: protected method `printArea' called for #
<Box:0xb7f11280 @height=20, @width=10> (NoMethodError)

warisan kelas

Warisan, pemrograman berorientasi objek merupakan salah satu konsep yang paling penting. Warisan memungkinkan kita untuk mendefinisikan kelas berdasarkan kelas lain, yang membuat menciptakan dan memelihara aplikasi jauh lebih mudah.

Warisan membantu untuk menggunakan kembali kode dan eksekusi cepat, sayangnya, Ruby tidak mendukung multiple inheritance, namunmixin dukungan Ruby.mixin seperti implementasi tertentu dari beberapa warisan, beberapa warisan, hanya bagian dari antarmuka diwariskan.

Ketika Anda membuat kelas, programmer dapat menentukan kelas baru yang mewarisi dari kelas yang ada dari anggota, jadi jangan menulis dari awal data anggota baru dan fungsi anggota. Kelas yang ada disebutkelas dasar atau kelas parent, kelas baru ini disebut kelas atau subclass berasal.

Ruby juga menyediakan subclass konsep subclass yang mewarisi, contoh berikut mengilustrasikan konsep ini. Memperluas sintaks kelas sangat sederhana. Hanya menambahkan <nama karakter dan kelas induk pernyataan kelas kaleng. Sebagai contoh, berikut mendefinisikan kelasBigBoxBox adalah subclass:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end
   # 实例方法
   def getArea
      @width * @height
   end
end

# 定义子类
class BigBox < Box

   # 添加一个新的实例方法
   def printArea
      @area = @width * @height
      puts "Big box area is : #@area"
   end
end

# 创建对象
box = BigBox.new(10, 20)

# 输出面积
box.printArea()

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Big box area is : 200

metode overloading

Meskipun Anda dapat menambahkan fitur baru di kelas turunan, tapi kadang-kadang Anda mungkin ingin mengubah perilaku telah didefinisikan dalam metode kelas induk. Kemudian Anda dapat menjaga nama metode yang sama, fungsi tersebut dapat kelebihan beban metode, seperti yang ditunjukkan dalam contoh berikut:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end
   # 实例方法
   def getArea
      @width * @height
   end
end

# 定义子类
class BigBox < Box

   # 改变已有的 getArea 方法
   def getArea
      @area = @width * @height
      puts "Big box area is : #@area"
   end
end

# 创建对象
box = BigBox.new(10, 20)

# 使用重载的方法输出面积
box.getArea()

Jalankan contoh di atas output:

Big box area is : 200

Overloading Operator

Kami ingin menggunakan operator + melakukan penjumlahan vektor dari dua benda Box, gunakan * operator untuk lebar dan tinggi dari Box dikalikan menggunakan unary operator - lebar dan tinggi dari Box dinegasikan. Berikut ini adalah versi kelas matematika dengan definisi Box Operator:

class Box
  def initialize(w,h) # 初始化 width 和 height
    @width,@height = w, h
  end

  def +(other)         # 定义 + 来执行向量加法
    Box.new(@width + other.width, @height + other.height)
  end

  def -@               # 定义一元运算符 - 来对 width 和 height 求反
    Box.new(-@width, -@height)
  end

  def *(scalar)        # 执行标量乘法
    Box.new(@width*scalar, @height*scalar)
  end
end

objek beku

Kadang-kadang, kita ingin mencegah sebuah objek berubah. Dalam Object, metode pembekuan dapat mencapai hal ini, secara efektif dapat menempatkan objek ke dalam sebuah konstanta. Setiap objek dapat dibekukan dengan memanggilObject.freeze.objek beku tidak dapat diubah, yaitu, Anda tidak dapat mengubah variabel instance-nya.

Anda dapat menggunakanObject.frozen? Cara untuk memeriksa apakah objek tertentu telah dibekukan.Jika objek telah dibekukan, metode mengembalikan benar, jika tidak mengembalikan nilai palsu. Contoh berikut menggambarkan konsep ini:

#!/usr/bin/ruby -w

# 定义类
class Box
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end

   # 访问器方法
   def getWidth
      @width
   end
   def getHeight
      @height
   end

   # 设置器方法
   def setWidth=(value)
      @width = value
   end
   def setHeight=(value)
      @height = value
   end
end

# 创建对象
box = Box.new(10, 20)

# 让我们冻结该对象
box.freeze
if( box.frozen? )
   puts "Box object is frozen object"
else
   puts "Box object is normal object"
end

# 现在尝试使用设置器方法
box.setWidth = 30
box.setHeight = 50

# 使用访问器方法
x = box.getWidth()
y = box.getHeight()

puts "Width of the box is : #{x}"
puts "Height of the box is : #{y}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Box object is frozen object
test.rb:20:in `setWidth=': can't modify frozen object (TypeError)
        from test.rb:39

konstanta kelas

Anda dapat mendefinisikan kelas internal yang konstan, dengan nilai numerik atau string yang langsung ke definisi variabel, yang tidak memerlukan konstan menggunakan @ atau @@. Dengan konvensi, nama penggunaan huruf besar konstan.

Setelah konstan didefinisikan, Anda tidak dapat mengubah nilainya, Anda dapat langsung mengakses konstanta internal kelas, seperti akses ke variabel yang sama, tetapi jika Anda ingin mengakses kelas konstan eksternal, maka Anda harus menggunakanClassName :: konstan , seperti yang ditunjukkan dalam contoh berikut.

#!/usr/bin/ruby -w

# 定义类
class Box
   BOX_COMPANY = "TATA Inc"
   BOXWEIGHT = 10
   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end
   # 实例方法
   def getArea
      @width * @height
   end
end

# 创建对象
box = Box.new(10, 20)

# 调用实例方法
a = box.getArea()
puts "Area of the box is : #{a}"
puts Box::BOX_COMPANY
puts "Box weight is: #{Box::BOXWEIGHT}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Area of the box is : 200
TATA Inc
Box weight is: 10

konstanta kelas dapat diwariskan, tetapi juga sama dengan metode contoh kelebihan beban.

Gunakan mengalokasikan membuat objek

Mungkin ada kasus, Anda ingin membuat sebuah objek tanpa memanggil konstruktormenginisialisasi objek, yang objek dibuat menggunakan metode baru, dalam hal ini, Anda dapat memanggil mengalokasikan untuk membuat obyek diinisiasi, seperti contoh berikut sebagai berikut:

#!/usr/bin/ruby -w

# 定义类
class Box
   attr_accessor :width, :height

   # 构造器方法
   def initialize(w,h)
      @width, @height = w, h
   end

   # 实例方法
   def getArea
      @width * @height
   end
end

# 使用 new 创建对象
box1 = Box.new(10, 20)

# 使用 allocate 创建两一个对象
box2 = Box.allocate

# 使用 box1 调用实例方法
a = box1.getArea()
puts "Area of the box is : #{a}"

# 使用 box2 调用实例方法
a = box2.getArea()
puts "Area of the box is : #{a}"

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Area of the box is : 200
test.rb:14: warning: instance variable @width not initialized
test.rb:14: warning: instance variable @height not initialized
test.rb:14:in `getArea': undefined method `*' 
   for nil:NilClass (NoMethodError) from test.rb:29

Informasi kelas

diri Ruby dan Java ini mirip, tetapi berbeda. metode Java dirujuk dalam metode contoh, jadi ini biasanya mengacu pada objek saat. Ruby kode baris demi baris, sehingga dalam konteks (konteks) diri yang berbeda memiliki arti yang berbeda. Mari kita lihat contoh berikut:

#!/usr/bin/ruby -w

class Box
   # 输出类信息
   puts "Class of self = #{self.class}"
   puts "Name of self = #{self.name}"
end

Ketika kode di atas dijalankan, maka akan menghasilkan hasil sebagai berikut:

Class of self = Class
Name of self = Box

Ini berarti bahwa kelas dapat didefinisikan oleh kelas sebagai objek saat untuk mengeksekusi, tetapi juga berarti bahwa meta-kelas dan definisi metode kelas induk selama pelaksanaan proses tersedia.