集算器的网格变量的存储无处不在。单元格的值可以很方便地在计算中引用,但是,也会带来占用内存的问题。当一个格子中的数据已经完成了参与计算的使命时,我们可以把它清除掉以减少对内存的占用。如果在获得中间数据之后,还需要继续复杂的计算,就尤其需要注意,应该把不再使用的单元格值清除掉,以减少对系统内存的消耗,这样可以有效地避免内存溢出。
看下面这个问题:列出所有员工中年龄前200人的名单,按姓名排列。员工资料来源于employee和employee2两个表,需要先把两个表中的数据汇总后,取得年龄前200名的员工资料,再按照姓名排序。
A | B | C | |
1 | =connect("esProc") | ||
2 | =A1.query("select * from employee") | ||
3 | =A1.query("select * from employee2") | ||
4 | =A2.new(Eid,Name+" "+FirstName:FullName,Birthday) | ||
5 | =A4.sort(Birthday)(to(200)) | ||
6 | =A5.sort(FullName) | ||
7 | >A1.close |
其中各单元格运算结果如下:
A2中的序表为employee中的员工资料:
A3的序表为employee2中的员工资料:
A4,所有员工的编号、全名、生日:
A5,年龄前200名的编号、全名和生日,按年龄排序:
A6,年龄前200名的员工按照全名排序:
实际上,我们最终需要的结果仅是A6中的数据。在A4整理出所有员工的必要信息之后,原始表格A2与A3中的信息就已经不再需要了;而在A5获取到年龄前200的员工信息之后,A4中的全部员工信息也不再需要。如果在中间数据获得之后,清除掉不再使用的初始数据,可以降低对系统内存的占用,使得运算更为稳定。
因此,网格程序可以按照下面的方法整理:
A | B | C | |
1 | =connect("esProc") | ||
2 | =A1.query("select * from employee") | ||
3 | =A1.query("select * from employee2") | ||
4 | =A2.new(Eid,Name+" "+FirstName:FullName,Birthday) | >A2.reset() | >A3=null |
5 | =A4.sort(Birthday)(to(200)) | >A4=null | |
6 | =A5.sort(FullName) | ||
7 | >A1.close |
当把单元格值设为null时,单元格中的值就会被完全清空,如C4中的语句。
值得注意的是B5中的语句,在这里虽然把A4中的值置空,却是无法达到减少内存占用的效果的。原因在于,序表的任何一条记录r中会都存储整个序表的信息,这样才能够进行r.home()等运算。序列A4中的元素由两个序表中的记录构成,虽然在A5中只用到了其中的200个,但是由于这些记录中存在着对序表的引用关系,即使A4置空,这两个序表也是不会清除的,而A4中原本存在的所有记录也就一直会存在于内存中。因此,如果利用将单元格值置空来清除内存,一定要明确原单元格中的数据是否仍然被使用。
而B4中,序表A2的reset()函数则不同,它会清除掉A2中的所有记录,但仍保留其数据结构,执行完B4后A2的值如下:
在清除格值时,可以根据需要选择这两种方法。
另外需要注意的是,在A6中对A5中的记录进行了排序操作,但是,在排序操作中,并不会产生新记录,在A6中存储的只是记录排序后的指针。因此,即使清除A5中的数据,记录由于被A6引用,仍会存在于内存中,实际被清除的仅仅是A5中的记录指针,对内存占用的影响较小。