跳转至

IDL 中的对象重载

原文链接: https://www.nv5geospatialsoftware.com/Learn/Blogs/Blog-Details/overloading-objects-in-idl

11580 给本文评分:

暂无评分

IDL 中的对象重载

匿名作者 2015年6月4日,星期四

大学时的一个学期,我参加了一个关于 Python 面向对象编程的非正式课程。第一天,教授问我们中是否有人有面向对象编程的经验。我告诉他我用 IDL,他不以为然地笑了,说:"IDL 不是真正的面向对象语言。"

我个人认为 IDL 具备许多面向对象的特性,并且我仍在学习新技术。由于 IDL 是一种解释型语言,我得说开发类非常容易,在 IDL 中进行面向对象编程确实没什么好怕的。

在本周的 IDL Data Point 文章中,我将讨论重载现有类的操作符。IDL 中的任何对象,包括安装时提供的对象,都可以通过编写一个在对象类定义中使用 inherits 关键字的新对象类来重载。事实上,有些对象,例如 IDL_OBJECT,就是专为被重载而设计的。

下面是一个我编的例子:我想使用一个列表(List),但我希望我的列表比 IDL 中简单的 LIST 对象功能更强一点(注意 IDL 文档将列表和哈希表指定为"复合数据类型",但在底层,它们就是对象类)。这个花哨的列表只允许添加数字。它还必须具备将所有值乘以指定因子的能力,以及将所有值递增一的能力。

定义类

由于想不出更好的名字,我将这个新列表称为 "Fancy_List"。其定义如下:

pro Fancy_List__Define      !null = {Fancy_List, inherits List}    end

现在,"Fancy_List" 被定义为一个列表的子类。

fl = Obj_New('Fancy_List') PRINT, Isa(fl, 'List')

IDL 打印出 1。

这意味着一个花哨的列表 就是 一个列表,而且是一个非常花哨的列表。

重载 ::Add 方法

由于这个列表只应允许数值,因此需要重载 Add 方法。这可以通过编写一个 Fancy_List::Add 方法来实现。在本例中,任何传入的非数值将被静默忽略。执行检查后,代码随后调用其父类的 ::Add 方法。关键字参数则通过 _REF_EXTRA 原样传递(这里使用 _REF_EXTRA 而不是 _EXTRA,是为了避免不必要的关键字副本)。

pro Fancy_List::Add, value, index, _REF_EXTRA=extra      if ~Isa(value, /NUMBER) then return      self.List::Add, value, index, _EXTRA=extra    end

实现 ::Multiply 方法

我将编写一个名为 ::Multiply 的新方法,将所有值乘以给定的因子。这个方法名是花哨列表独有的,因为 LIST 没有这样的方法,所以它并不重载任何东西。

pro Fancy_List::Multiply, multiplier      for i=0, self.Count()-1 do begin     self[i] *= multiplier   endfor    end

重载操作符

由于 List 继承自 IDL_Object,而 Fancy_List 又继承自 List,因此这个花哨的列表可以重载 IDL_Object 的任何操作符。以下是重载 ++ 操作符的示例。此操作将使花哨列表中的每个值递增一。

pro Fancy_List::_overloadPlusPlus      for i=0, self.Count()-1 do begin     self[i]++   endfor    end

运行示例

现在所有部分都组装好了,我们点击 Compile 按钮来试试吧!

fl = Fancy_List() fl.Add, 'A' print, fl.Count()

IDL 打印出 0,因为花哨列表忽略了字符串值 'A'。

fl.Add, [1,2,3,4], /EXTRACT PRINT, fl

IDL 打印出:

1        2        3        4

fl.Multiply, 2

PRINT, fl

IDL 打印出:

2        4        6        8

fl++ PRINT, fl

IDL 打印出:

3        5        7        9

探索 BlackBridge GeoCloud 在分配数组子集时提升性能