zoukankan      html  css  js  c++  java
  • ruby基础(三)

    类和模块

    1.类

    类是面向对象中一个重要的术语。我们可以把类看作是对象的抽象,
    所有的这类对象都有这些特征。而对象则是类的具体实现,按照类的要求创建的
    对象就是该类的对象。类就像对象的雏形一样,决定了对象的行为。
    eg:用数组类创建数组对象

    arr=Array.new   #[]
    

    用class方法查看对象属于那个类

    arr=[1,2,3]
    p arr.class       #Array
    p Array.class     #Class
    

    所有的类都是Class类的对象。

    当判断某个对象是否属于某个类,我们可以使用instance_of?方法。

    arr=[1,2,3]
    p arr.instance_of? Array    #true
    p arr.instance_of? Object   #false
    

    继承

    通过扩展已经创建的类来创建新的类成为继承。继承后创建的新类被称为子类。
    被继承的类称为父类。
    BasicObject类是ruby中所有类的父类。他定义了作为ruby对象最基本的功能。
    Object是BasicObject的子类。定义一般类所需要的功能。
    根据类的反向继承关系追查对象是否属于某个类,则可以使用is_a?方法。

    arr=[1,2,3]
    p arr.is_a? Array   #true
    p arr.is_a? Object  #true
    

    创建类

    class 类名    
        类的定义
    end    
    

    类名的首字母必须大写.eg:

    class Sayhello
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #实例化对象
    java=Sayhello.new("java")
    ruby=Sayhello.new
    

    调用new方法创建对象时会默认调用initialize方法。
    @name时实例变量。hello方法时实例方法。实例方法中可以直接引用实例变量。
    引用未定义的实例变量会返回nil.

    存取器

    ruby中不能直接访问实例变量或对实例变量赋值。需要通过方法来操作。
    
    class Sayhello
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
      #获取实例变量的方法
      def name
        puts "获取实例变量@name"
        @name
      end
      #修改实例变量的方法
      def name=(value)
        puts "修改实例变量@name"
        @name=value
      end
    end
    
    
    #实例化对象
    java=Sayhello.new("java") #调用initialize方法
    p java.name    #调用name方法
    java.name="python" #调用name=方法
    p java.name    #调用name方法
    java.hello    #调用hello方法
    
    

    Ruby提供了更简便的实现方法

    定义 意义
    attr_reader :name 只读(定义name方法)
    attr_writer :name 只写(定义name=方法)
    attr_accessor :name 读写(定义上面的两个方法)

    eg:

    class Sayhello
      #name和name=
      attr_accessor :name
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    
    #实例化对象
    java=Sayhello.new("java") #调用initialize方法
    p java.name    #"java"
    java.name="python"
    p java.name    #"python"
    java.hello    #hell0,I  am python
    

    特殊变量self
    在类内部self指向类自身,在实例方法内部,self指向调用方法的实例。

    class Sayhello
      #name和name=
      attr_accessor :name
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{self.name}!"
      end
    end
    
    
    #实例化对象
    java=Sayhello.new("java") #调用initialize方法
    
    java.hello    #hell0,I  am  java
    

    等价于

    class Sayhello
      #name和name=
      attr_accessor :name
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    
    #实例化对象
    java=Sayhello.new("java") #调用initialize方法
    
    java.hello    #hell0,I  am  java
    
    

    类方法

    class Sayhello
      class << Sayhello
        def hello(name)
          puts "#{name} said hello."
        end
      end
    
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #实例化对象
    java=Sayhello.new("java") #调用initialize方法
    java.hello    #hell0,I  am  java
    #调用类方法
    Sayhello.hello "ruby" #ruby said hello;
    

    在类内部定义类方法

    class Sayhello
      class << self
        def hello(name)
          puts "#{name} said hello"
        end
      end
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #调用类方法
    Sayhello.hello "ruby" #ruby said hello
    

    或者

    class Sayhello
      def Sayhello.hello(name)
          puts "#{name} said hello"
      end
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #调用类方法
    Sayhello.hello "ruby" #ruby said hello
    

    或者

    class Sayhello
      def self.hello(name)
          puts "#{name} said hello"
      end
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #调用类方法
    Sayhello.hello "ruby" #ruby said hello
    

    使用class <<类名 ~ end 这种写法的类定义称为单例类定义。
    单例类定义中定义的方法称为单例类方法。

    常量
    class语句中可以定义常量

    class Sayhello
      Version="1.0"
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        puts "hello,I am #{@name}!"
      end
    end
    
    #实例化对象
    p Sayhello::Version  #"1.0"
    

    类变量
    类变量为所有类的实例所共享,从类的外部访问类变量时需要存储器,不能使用
    attr_accessor等,需要直接定义。

    class Sayhello
      @@count=0
      def Sayhello.count
        @@count
      end
      def initialize(myname="ruby")
        puts "调用我实例化对象"
        @name=myname
      end
    
      def hello
        @@count+=1
        puts "hello,I am #{@name}!"
      end
    
    end
    
    #实例化对象
    p Sayhello.count  #0
    ruby=Sayhello.new
    ruby.hello
    java=Sayhello.new "java"
    java.hello
    p Sayhello.count  #2
    

    限制方法的调用
    Ruby提供了三种方法的访问级别:

    关键字 访问级别
    public 以实例方法的形式向外公开该方法
    private 只在类内部可以用
    protected 类内部及子类中可以使用

    eg:

    class AccTest
      def pub
        puts "hello"
      end
      #设置方法的访问权限
      public :pub
      def priv
        puts "private"
      end
      #设置方法的访问权限
      private :priv
    end
    
    acc=AccTest.new
    acc.pub
    acc.priv       #NoMethodError
    

    希望统一定义多个方法的访问级别时。可以使用下面的语法。
    eg:

    class AccTest
      public  #以下的方法都被定义为public
      def pub
        puts "hello"
      end
      private  #以下方法都被定义为private
      def priv
        puts "private"
      end
    end
    
    acc=AccTest.new
    acc.pub
    acc.priv       #NoMethodError
    

    没有定义访问访问级别方法默认为public,但是initialize方法是个例外,
    他通常被定义为private.

    扩展类
    eg:在原有的类的基础上添加方法

    class String
      def count_word
        #用空格分割self
        ary=self.split(/s+/)
        #返回分解后的数组的长度
        return ary.size
      end
    end
    str="I am ruby"
    p str.count_word   #3
    

    继承

    class 类名 < 父类名
      类定义
    end
    

    eg:RingArray继承Array

    class RingArray < Array
      #重定义运算符[]
      def[](i)
        ind=i%self.size
        super(ind)
      end
    end
    
    arr=RingArray["金","木","水","火","土"]
    p arr[6]  #"木"
    p arr[12] #"水"
    

    定义类的时候没有指定父类的情况下,ruby会默认该类为Object类的子类。
    有时候我们希望继承更轻量级的类,就会使用BasicObject类
    eg:查看类的实例方法

    p Object.instance_methods
    p BasicObject.instance_methods  
    #[:!, :==, :!=, :__send__, :equal?, :instance_eval, :instance_exec, :__id__]
    

    需要继承BasicObject类,需要显式的继承。

    alias与undef
    使用alias给方法设置别名.或者在重定义已经存在的方法时,为了使用别名调用
    原来的方法,也需要用到alias.

    alias 别名  原名
    alias :别名 :原名
    
    class Sayhello
      def hello
        "hello"
      end
      alias sayhello hello
    end
    
    h=Sayhello.new
    p h.sayhello  #"hello"
    

    eg:

    class Sayhello
      def hello
        "hello"
      end
      alias sayhello hello
    end
    
    class Child < Sayhello
      alias  old_hello hello
      def hello
        "#{old_hello},again."
      end
    end
    
    child=Child.new
    p child.old_hello  #"hello"
    p child.hello      #"hello,again."
    

    undef
    undef用于删除已定义的方法。

    undef 方法名
    undef :方法名
    

    eg:子类中删除父类定义的方法

    class Sayhello
      def hello
        "hello"
      end
      alias sayhello hello
      def del
        "delete"
      end
    end
    
    class Child < Sayhello
      alias  old_hello hello
      def hello
        "#{old_hello},again."
      end
      undef del
    end
    
    child=Child.new
    p child.old_hello  #"hello"
    p child.hello      #"hello,again."
    p child.del      #NoMethodError
    

    单例类
    利用单例类给对象添加方法

    str1="Ruby"
    str2="Ruby"
    class << str1
      def hello
        "hello,#{self}!"
      end
    end
    
    p str1.hello     #"hello,Ruby!"
    p str2.hello     #(NoMethodError)
    

    Ruby中所有的类都是Class类的对象,因此,Class对象的实例方法以及
    类对象的单例方法都是类方法。

  • 相关阅读:
    [zoj3627]模拟吧
    [zoj3623]背包模型
    [hdu4358]树状数组
    [hdu1272]并查集
    [hdu3308]线段树
    [hdu5033]单调队列
    [hdu1506]单调队列(栈)
    [hdu2888]二维RMQ
    [hdu4123]dfs区间化+RMQ
    [hdu1242]优先队列
  • 原文地址:https://www.cnblogs.com/yiluhuakai/p/9414751.html
Copyright © 2011-2022 走看看