Ruby的模块包含机制

发表于:2014-3-19 11:37

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:言无不尽    来源:51Testing软件测试网采编

  在 Ruby 中,模块可以被其他模块包含(这里,其他模块也包括类,因为类也是模块)。通过包含模块,可以构建出复杂的类层次结构。本文解释了当包含一个模块时,Ruby 内部都做了哪些实际的工作
  下面这段 Ruby 代码创建了 A, B, C 三个模块,C 包含 A 和 B。
  A = Module.new
  B = Module.new
  module C
  include A, B    # Inclusion is done by this line
  end
  在模块 C 中,语句 include A, B 完成了模块包含的工作,该语句以 A, B 两个模块为作为参数,调用了模块 C 的 include 方法。一切都那么自然。
  现在,把注意力放在 include 方法上,它的默认实现是 Module#include。根据 API 文档,它以相反的顺序对参数逐一调用 append_features 方法。对应的 C 函数是 
rb_mod_include。
static VALUE
rb_mod_include(int argc, VALUE *argv, VALUE module)
{
int i;
ID id_append_features, id_included;
CONST_ID(id_append_features, "append_features");
CONST_ID(id_included, "included");
for (i = 0; i < argc; i++)
Check_Type(argv[i], T_MODULE);
while (argc--) {
rb_funcall(argv[argc], id_append_features, 1, module);
rb_funcall(argv[argc], id_included, 1, module);
}
return module;
}
  从 Ruby 源码来看,除了对参数模块调用 append_features 方法外,还紧接着调用了 included 方法。所以,文档描述得并不完整,可能还没有更新。
  append_features 和 included 都是回调方法。而 append_features 方法才是真正干活的地方,Ruby 通过这个方法将包含的逻辑转移到了被包含的模块上。这种精巧的设计能让你灵活地自定义包含模块的行为,既可以在发出包含动作的模块中重定义 include 方法,也可以从源头着手,重定义 append_features 方法。
  再来看看 append_features 的默认实现 Module#append_features 都做了什么。下面是 API 文档上给出的源码:
rb_mod_append_features(VALUE module, VALUE include)
{
switch (TYPE(include)) {
case T_CLASS:
case T_MODULE:
break;
default:
Check_Type(include, T_CLASS);
break;
}
rb_include_module(include, module);
return module;
}
31/3123>
《2023软件测试行业现状调查报告》独家发布~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2024
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号