首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 开发语言 > Ruby Rails >

Ruby学习(2)-类与对象

2012-08-21 
Ruby学习(二)------类与对象在Ruby中,操作的都是对象,结果也都是对象。类定义Ruby中,类的定义要在class...e

Ruby学习(二)------类与对象

在Ruby中,操作的都是对象,结果也都是对象。

类定义

Ruby中,类的定义要在class...end之间,类名必须以大写字母开始。

若某个类已经被定义过,此时又用相同的类名进行类定义的话,是对原有的类的定义进行追加.

?

class ClassName         def method1                 puts 'method1'         endendclass ClassName  def method2                 puts 'method2'         end?end

?

对象,属性和方法

1、类在实例化后生成对象。

2、方法是对对象进行的操作。操作对象(被调)以self来表示。对象的性质由其内部定义的方法所决定 。

?

class Person         def initialize(name,gender,age)       ###构造实例对象时被自动调用               @name = name                         ###以@开头的是实例变量,只能在类在方法内部使用它               @gender = gender               @age = age          endendpeople = Person.new('Jarvi','female','26')  ###创建一个Person对象

?

?3、在Ruby中,一个对象的内部属性都是私有的。实例变量可以用只读控制符attr_reader来表示变量为可读,

类似地,也可以用成员变量写控制符attr_writer来表示可写。表示可读、可写用attr_accessor

?

class Person         def initialize(name,gender,age)                      @name = name                                        @gender = gender               @age = age          end          attr_reader :name    #可读          attr_writer  :gender   #可写          attr_accessor :age     #可读、可写          ### attr_accessor :name, :gender,:age    #多个表示end
?

?

也可以用attr控制符来表示变量是否可读写,它可有二个参数,一个符号参数,第二个是一个bool参数,表示为符号参数,用于指示是否为符号参数产生写方法。默认是false,只产生读方法,不产生写方法。

?

class Person           attr :name, true #可读写           attr :gender,false  #只读end

?

?PS:attr_reader,attr_writer,attr_accessor 和 attr不是语言的关键字,而是Module模块方法。

?

class Test          attr_accessor :valueendputs Test.instance_methods -Test.supperclass.public_methods结果为:valuevalue =

?

?Test.instance_methods 得到Test类所有的实例方法。

Test.supperclass.public_methods得到Test父类所有的实例方法。

相减就得到Test类不包括父类的所有的实例方法。

?

4、重定义方法

重定义一个方法时,新的定义会覆盖原有的方法。

5、重定义类

重定义一个类时,表示对原有定义的追加,不会覆盖原来的方法。

6、self

self和Java中的this有些类似,代表当前的对象。

?

?

继承

1、Ruby使用 < 来表示继承。

class Te < Person
def initialize(name,gender,age,company)                  @name = name                  @gender = gender                  @age = age                  @company = company           endend

PS: Ruby只支持单继承,但提供mixin的机制来实现多继承。

?

2、super?

a、可以使用super 关键字调用对象父类的方法。当super省略参数时,将使用当前方法的参数来进行调用。

b、如果传入的参数被修改再调用super的话,那么将会使用修改后的值

?

class Base     def meth(info)        puts "This is Base #{info}"    endendclass Derived < Base    def meth(info)          puts "This is derived #{info}"          info = 'test2'          super     endendobj1 = Derived.newobj1.meth("test")结果:This is derived testThis is derived test2
?

?

特殊方法和特殊类

?

特殊方法

特殊方法是指只从属于某个特定对象的方法。

1、定义一个特殊方法

?

class SingletonTest    def info          puts "This is This is SingletonTest method"   endend
obj1 = SingletonTest.newobj2 = SingletonTest.newdef obj2.info     puts "This is obj2"end
obj1.infoobj2.info执行结果为:This is This is SingletonTest methodThis is obj2

?

?2、定义多个特殊方法,使用<<

?

class SingletonTest        def meth1             puts "This is meth1"        end        def meth2             puts "This is meth2"        endendobj1 = SingletonTest.newobj2 = SingletonTest.newclass << obj2        def meth1                puts "This is obj2's meth1"        end        def meth2                puts "This is obj2's meth2"        endendobj1.meth1obj1.meth2obj2.meth1obj2.meth2执行结果为:This is meth1This is meth2This is obj2's meth1This is obj2's meth2
?

?

类变量与类方法

?

类变量

1、类变量被一个类的所有实例对象共享,类变量名以'@@'开始,使用前必须初始化。 类似与java里面的static修饰的变量。

?

class Person            @@number = 0 #使用前必须有初值            def initialize(name, gender, age)                   @name = name                   @gender = gender                   @age = age                   @@number += 1            endend

?

?2、类变量是私有的,只能通过实例方法和类方法进行访问。相当于java里面的static修饰的方法

?

class Test         @@number = 0         def initialize(name,age)            @name = name            @age = age            @@number +=1         end         def Test.getNumber()            return @@number         end         def getNumber()            return @@number         endendtest1 = Test.new('jim',20)test2 = Test.new('tom',30)puts Test.getNumber()puts test1.getNumber()

?

?存取控制

Ruby中,只能通过方法改变一个类的属性,不能直接改变。

方法的存取控制有三种:

?

公有方法? ? ? ? ? ? ?方法在任何地方都可以被调用,这是方法的默认存取控制。 除了initialize和initialize_cpoy方法,他们永远是私有方法。保护方法? ? ? ? ? ?方法只能被定义这个方法的类自己的对象和这个类的子类的对象所访问。私有方法? ? ? ? ? ?方法只能被定义这个方法的类的对象自己访问,即使是这个类的其他对象也不能访问。
Ruby 指定方法访问权限的方式有两种,一种是在定义方法之前声明方法的访问权限,另一种是在方法定义后指定访问权限。
#前式class Test         def method1    #默认为公有方法                …         end         protected #保护方法         def method2          …         end         private #私有方法         def method3           …         end         public         def test_protected(arg) #arg是Test类的对象             arg.method2   #正确,可以访问同类其他对象的保护方法         end         def test_private(arg) #arg是Test类的对象             arg.method3  #错误,不能访问同类其他对象的私有方法         endendobj1 = Test.newobj2 = Test.newobj1.test_protected(obj2)obj1.test_private(obj2)

#后式class Test        def method1             ...        end        def method2            ...        end        def method3            ...        end        def methdo4           ...        endpublic :method1protected :method2private :method3, :method4end
?元类在Ruby中,一切都是对象,类和实例对象都是对象。所有类对象的类是Class类,Oject类是所有类的基类。
所以类方法有如下的定义
class Test             #定义类方法方式1             def Test.meth1                        # ...            end            #定义类方法方式2           def self.meth2                      # ...           end           #定义类方法方式3         class << Test           def meth3                   # ...           end         end        #定义类方法方式4         class << self         def meth4              # ...          end      endend
?Ruby的动态性1、可以重新定义同一个方法2、可以使用undef_method取消一个方法的定义
class UndefTest             def meth                    puts "This is meth"              endendobj1 = UndefTest.newobj1.methclass UndefTest          undef_method(:meth)endobj1.meth执行结果为:This is methtest.rb:14: undefined method `meth' for #<UndefTest:0x2ac8240> (NoMethodError)
?变量
局部变量变量以小写字母或下划线开始。局部变量的作用域起始于声明处,结束于该声明所在的块、方法定义、类/模块定义的结尾。即使声明部分未被解释器执行仍有效,因为已经经过解释器的处理。但若块已经变成过程对象的话,则局部变量将一直持续到该过程对象终结为止。若多个过程对象引用同一个作用域的话,局部变量将被这些对象所共享。实例变量以@开始的变量是实例变量,实例变量属于特定的对象。类变量以@@开始的变量是类变量。 类变量在类的定义中定义,可以在类的特殊方法、 实例方法等处对类变量进行赋值和引用。类变量被类,类的子类和他们的实例对象共享。类变量是私有的,在类外无法直接访问,你只能通过实例方法和类方法去访问它。可以把类变量看作一种被类、子类以及它们的实例所共享的全局变量。模块中定义的类变量(模块变量)被所有包含该模块的类所共享。
全局变量以$开始的变量是全局变量,全局变量可以在程序的任何地方加以引用。 全局变量无需变量声明。引用尚未初始化的全局变量时,其值为nil。常量常量以大写字母开始,常数的定义和初始化由赋值过程完成。? ? ? ? ? ? ? ??常量可以定义在类和模块中,不能定义在方法中。? ? ? ? ? ? ? ??若对已定义的常数进行赋值的话,会出现警告信息。若引用未定义的常数会引发NameError异常。若想在外部访问类或模块中的常数时,要使用“::”操作符。在类定义表达式生成类对象的同时,还会将类对象赋值给一个与该类同名的常数,引用类名也就是引用该常数。若想访问Object类中的常数(顶层的常数)时,也需要也使用"::"操作符,但操作符左边为空。
与定义有关的操作to-do

?

热点排行