Home > Programming, QA, Test and Automation Stuffs > What is a Module on Ruby ?

What is a Module on Ruby ?

Hello guys, I will summarise this post because there are many examples and methods that you can learn. So, today I will talk about more technical questions. What is and when you can use module on Ruby.

WHAT IS ?

Module is a collection of methods and constants. The methods in a module may be instance methods or module methods. Instance methods appear as methods in a class when the module is included, module methods do not. Conversely, module methods may be called without creating an encapsulating object, while instance methods may not. (See below, module_function)

USING PARAMETERS

Once a module is written, its global entities (i.e., global PARAMETERs, global variables and internal functions) can be made available to other modules and programs. The program or module that wants to use a particular module must have a USE statement at its very beginning. The USE statement has one of the following forms:

SYNTAX

The following form is the syntax of a module:

USE  module-name

USE  module-name, ONLY: name-1, name-2, ..., name-n

Here is the meaning of these USEs:

  • The first indicates that the current program or module wants to use the module whose name is module-name. For example, the following main program indicates that it wants to use the content of module SomeConstants:
    PROGRAM  MainProgram
       USE   SomeConstants
       IMPLICIT  NONE
       ..........
    END PROGRAM  MainProgram
    

    Once a USE is specified in a program or in a module, every global entities of that used module (i.e.PARAMETERs, variables, and internal functions) becomes available to this program or this module. For example, if module SomeConstants is:

    MODULE  SomeConstants
       IMPLICIT  NONE
       REAL, PARAMETER :: PI = 3.1415926
       REAL, PARAMETER :: g = 980
       INTEGER         :: Counter
    END MODULE  SomeConstants
    

    Then, program MainProgram can access to PARAMETERPI and g and variable Counter.

  • However, under many circumstances, a program or a module does not want to use everything of the used module. For example, if program MainProgram only wants to use PARAMETER PIand variable Counter and does not want to use g, then the second form becomes very useful. In this case, one should add the keyword ONLY followed by a colon :, followed by a list of names that the current program or module wants to use.
    PROGRAM  MainProgram
       USE   SomeConstants, ONLY: PI, Counter
       IMPLICIT  NONE
       ..........
    END PROGRAM  MainProgram
    

    Thus, MainProgram can use PI and Counter of module SomeConstants; but, MainProgram cannot use g!USE with ONLY: is very handy, because it could only “import” those important and vital information and “ignore” those un-wanted ones.

  • There is a third, not recommended form, that can help to rename the names of a module locally. If a module has a name abc, in a program with a USE, one can use a new name for abc. The way of writing this renaming is the following:
    new-name => name-in-module
    

    For example, if one wants to give a new name to Counter of module SomeConstants, one should write:

    NewCounter => Counter
    

    Thus, in a program, whenever it uses MyCounter, this program is actually using Counter of module SomeConstants.This kind of renaming can be used with ONLY: or without ONLY:.

    PROGRAM  MainProgram
       USE   SomeConstants, ONLY: PI, MyCounter => Counter
       IMPLICIT  NONE
       ..........
    END PROGRAM  MainProgram
    

    The above example wants to use PI of module SomeConstants. In this case, when program MainProgram uses PI, it actually uses the PI of module SomeConstants. Program MainProgramalso uses Counter of module SomeConstants; but, in this case, since there is a renaming, when MainProgram uses MyCounter it actually uses Counter of module SomeConstants.Renaming does not require ONLY:. In the following, MainProgram can use all contents of module SomeConstants. When MainProgram uses PI and g, it uses the PI and g of module SomeConstants; however, when MainProgram uses MyCounter, it actually uses Counter of module SomeConstants.

    PROGRAM  MainProgram
       USE   SomeConstants, MyCounter => Counter
       IMPLICIT  NONE
       ..........
    END PROGRAM  MainProgram
    

    Why do we need renaming? It is simple. In your program, you may have a variable whose name is identical to an entity of a module that is being USEed. In this case, renaming the variable name would clear the ambiguity.

    PROGRAM  MainProgram
       USE   SomeConstants, GravityConstant => g
       IMPLICIT  NONE
       INTEGER :: e, f, g
       ..........
    END PROGRAM  MainProgram
    

    In the above example, since MainProgram has a variable called g, which is the same as PARAMETER g in module SomeConstants. By renaming g of SomeConstantsMainProgram can use variable g for the variable and GravityConstant for the PARAMETER g in module SomeConstants.

However, renaming is not a recommended feature. You should avoid using it whenever possible.

EXAMPLES

module Mod

  include Math
  CONST = 1
  def meth
    #  ...
  end
end
Mod.class              #=> Module
Mod.constants          #=> [:CONST, :PI, :E]
Mod.instance_methods   #=> [:meth]

 

Public Class Methods

I will write two examples, but if you click in the link below (Fonts), you can see a lot of other examples of modules used on Ruby.

new → mod
new {|mod| block } → mod

Creates a new anonymous module. If a block is given, it is passed the module object, and the block is evaluated in the context of this module using module_eval.

fred = Module.new do
  def meth1
    "hello"
  end
  def meth2
    "bye"
  end
end
a = "my string"
a.extend(fred)   #=> "my string"
a.meth1          #=> "hello"
a.meth2          #=> "bye"

 

Assign the module to a constant (name starting uppercase) if you want to treat it like a regular module.

static VALUE
rb_mod_initialize(VALUE module)
{
    if (rb_block_given_p()) {
        rb_mod_module_exec(1, &module, module);
    }
    return Qnil;
}
module_function(string, …) → self

Creates module functions for the named methods. These functions may be called with the module as a receiver, and also become available as instance methods to classes that mix in the module. Module functions are copies of the original, and so may be changed independently. The instance-method versions are made private. If used with no arguments, subsequently defined methods become module functions. String arguments are converted to symbols.

module Mod
  def one
    "This is one"
  end
  module_function :one
end
class Cls
  include Mod
  def call_one
    one
  end
end
Mod.one     #=> "This is one"
c = Cls.new
c.call_one  #=> "This is one"
module Mod
  def one
    "This is the new one"
  end
end
Mod.one     #=> "This is one"
c.call_one  #=> "This is the new one"

               static VALUE
rb_mod_modfunc(int argc, VALUE *argv, VALUE module)
{
    int i;
    ID id;
    const rb_method_entry_t *me;

    if (!RB_TYPE_P(module, T_MODULE)) {
        rb_raise(rb_eTypeError, "module_function must be called for modules");
    }

    if (argc == 0) {
        SCOPE_SET(NOEX_MODFUNC);
        return module;
    }

    set_method_visibility(module, argc, argv, NOEX_PRIVATE);

    for (i = 0; i < argc; i++) {
        VALUE m = module;

        id = rb_to_id(argv[i]);
        for (;;) {
            me = search_method(m, id, 0);
            if (me == 0) {
                me = search_method(rb_cObject, id, 0);
            }
            if (UNDEFINED_METHOD_ENTRY_P(me)) {
                rb_print_undef(module, id, 0);
            }
            if (me->def->type != VM_METHOD_TYPE_ZSUPER) {
                break; /* normal case: need not to follow 'super' link */
            }
            m = RCLASS_SUPER(m);
            if (!m)
                break;
        }
        rb_method_entry_set(rb_singleton_class(module), id, me, NOEX_PUBLIC);
    }
    return module;
}
            


Guys, if you have any question, suggestion or complaint (I hope this last you don’t have) just write in the comments. Bye 🙂


 

Fonts: http://www.ruby-doc.org/core-2.1.2/Module.html

http://www.cs.mtu.edu/~shene/COURSES/cs201/NOTES/chap06/mod-use.html

Advertisements
  1. No comments yet.
  1. July 2, 2014 at 10:46 pm

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: