Ruby class inheritance, abstract classes, class expansion, proxy class instances, ruby instances
Summarize the class extensions encountered in the work:
1. class inheritance:
When multiple classes share many methods, you can extract the public methods and inherit the required classes.
Example:
Copy codeThe Code is as follows:
Class A <ActiveRecord: Base
Def
P "it was"
End
End
Class B <
End
Class C <
End
B. new. a # => "it was"
C. new. a # => "it was"
2. abstract class
When multiple classes need to inherit one class, the first method will encounter a problem.
(Reference someone else's Annotation to describe the use of abstract classes https://ihower.tw/rails4/activerecord-others.html)
A Single table bearing STI (Single-table inheritance)
It is a big question how to introduce the concept of moving objects to the design of relational databases. In Rails, the most simple solution is built. Only one data table is used to store the objects in the bearing system, match A type field to indicate the type of the resource.
To enable the parameter STI function, as long as there is a parameter bit named "type" in the example, the parameter string can be used. The posts data table below the false settings has a metadata table named type. In fact, these three Models will share the posts data table. Of course, also, these two sub-classes also inherit the validates_presence_of: subject of the parent class:
Copy codeThe Code is as follows:
Class Post <ActiveRecord: Base
Validates_presence_of: subject
End
Class GuestPost <Post
End
Class MemberPost <Post
End
Let's take a look at the rails console. Rails will automatically set the type setting bit based on the differences you use:
Copy codeThe Code is as follows:
Post = GuestPost. create (: subject => "guest ")
Post. type # "GuestPost"
Post. id #1
Post = MemberPost. create (: subject => "member ")
Post. id #2
Post. type # "MemberPost"
GuestPost. last #1
Sorry, because of the relevance of this example, you cannot use the name "type.
The biggest problem of STI lies in the wave position. If there are not many overlapping places in the traditional system, then using STI will be a lot of waves. If there are many non-shared buckets, the Creator will suggest not to use this function, so that other users have their own data tables. To enable repeated STI, add self. Strict act_class = true to the parent class.
Copy codeThe Code is as follows:
Class Post <ActiveRecord: Base
Self. abstract_class = true
End
Class GuestPost <Post
End
Class MemberPost <Post
End
Here, GuestPost and MemberPost must have their own Migrations to create guest_posts and member_posts data tables.
You can also introduce multiple dependencies in a class.
Copy codeThe Code is as follows:
Class Dependency <Post
Require_dependency 'guestpost'
Require_dependency 'memberpost'
End
3. Class expansion and integration
Ruby classes are single-inherited. To implement the multi-inheritance function, you need to use the mixin (join mode) method, that is, class expansion and mixing. Example:
Copy codeThe Code is as follows:
Module Extract
Def self. included (base)
Base. extend (ClassMethods)
End
Module ClassMethods
Def
P "it was"
End
End
End
Class A <ActiveRecord: Base
Include Extract
End
A. new. a # => "it was"
4. Proxy
When a function is complex, of course, writing to lib is easy to process as a function-oriented method. You can also use the proxy class to implement object-oriented calls.
Example:
Copy codeThe Code is as follows:
Class A <ActiveRecord: Base
Def generate_schedule
Generator = Generator: ExcelGenerator. new (self)
Generator. generate_schedule
End
End
Module Generator
Class ExcelGenerator
Attr_reader: excel,: workbook,: a,: worksheet
Attr_accessor: styles
Def initialize ()
@ Excel | = Axlsx: Package. new
@ Workbook | = @ excel. workbook
@ Worksheet = @ workbook. add_worksheet (: name => 'test to generate an excel file ')
@ A | =
@ Styles | = Hash. new
End
Def generate_schedule
# Excel content definition
End
End
End
A. new. generate_schedule you can use the proxy class ExcelGenerator to implement A class instance method generate_schedule
Of course, you can also add a class instance method by using the include model method. Sometimes you can use it together. In addition, the advantage of using the proxy class is that when multiple classes need the same method, the common part can be defined. For example, sending an email:
Copy codeThe Code is as follows:
Class A <ActiveRecord: Base
Include SendEmail
End
Class B <ActiveRecord: Base
Include SendEmail
End
Implementation introduction module:
Copy codeThe Code is as follows:
Module SendEmail
# Include this module to class: A and B
# Use like that -- A. first. send_email
Def send_email
Email. call_email (self)
End
End
Implement proxy class:
Copy codeThe Code is as follows:
Class Email <ActionMailer: Base
Default: from => test@email.com"
Def self. call_email (obj)
Define_method "# {obj. state}" do | obj |
@ Obj = obj
Mail (: to => @ obj. email,: subject => "XX title ")
End
Send ("# {obj. state}"). deliver
# Define different methods in different States based on different object obj. state, and then send a template that calls the status of related objects.
End
End
RUBY is flexible. Of course, there are many other methods to achieve more, and I will summarize them later.