具体实施方式
对地理围栏的网格索引可以基于3个指标来衡量:索引覆盖率、索引准确率和索引网格数量。设用来表示一个地理围栏的网格集合中集合元素的个数为N(N为自然数),也即该地理围栏的索引网格数量为N,则该网格集合的索引覆盖率C可以表示为式1,索引准确率P可以表示为式2:
式1和式2中,SO为所有网格索引与围栏重合部分的面积之和,即其中aooi为第i个索引网格与围栏重合部门的面积,i∈[1,N];SF为围栏的面积;SI为所有索引网格的面积之和,即其中aogi为第i个索引网格的面积,i∈[1,N]。
本申请实施例中要解决的技术问题可以表述为:在满足网格集合完全覆盖围栏(即C=1)、并且索引准确率不低于预定精度阈值THRP(即P≥THRP)的条件下,降低N的大小。
在将一个地理围栏表示为索引网格的网格集合时,集合中的索引网格可以划分为两类,一类是处于围栏内的网格,即覆盖范围完全处在围栏内部的网格;另一类是包含围栏边界的网格,即覆盖范围有的在围栏内部,有的在围栏外部。对处于围栏内部的网格,不论这些网格的粒度是多少,都不会影响网格集合的索引准确率。网格集合的索引准确率由包含围栏边界的各个网格的粒度决定。可以通过增加包含围栏边界的网格的粒度来提高索引准确率(增加粒度即采用更为密集的网格或更细的网格),而使处于围栏内部的网格采用较粗的粒度来降低索引网格的数量N。
因此,本申请实施例提出一种新的确定地理围栏的索引网格的方法,以包含围栏的最小单一网格作为围栏的外接网格,以外接网格为迭代的起点,将包含围栏边界的网格逐层向更细粒度划分,到网格集合的索引准确率满足预定精度阈值时迭代停止;通过只增加包含围栏边界的网格的粒度,而不对处于围栏内的网格做进一步的划分,将不同粒度的网格作为索引网格,减少了索引网格的数量,从而解决了现有技术中存在的问题。
本申请的实施例可以运行在任何具有计算和存储能力的设备上,如手机、平板电脑、PC(Personal Computer,个人电脑)、笔记本、服务器等设备;还可以由运行在两个或两个以上设备的逻辑结点来实现本申请实施例中的各项功能。
本申请的实施例中,确定地理围栏的索引网格的方法的流程如图1所示。
步骤110,确定围栏的外接网格。
网格系统是一种以平面子集的规则分级剖分为基础的空间数据结构,可以基于一定的粒度体系,由粗到细逐级将某个地理区域某个地理区域划分为若干个相互邻接的多边形网格,以便于进行位置信息的表达和与位置相关的数据的管理,并使得数据的组织、分析和应用具有高效性。
网格系统通常采用一定的粒度体系来进行地理区域的划分。每个粒度体系包括一系列由粗到细、逐级排列的粒度,划分网格时采用的粒度决定了网格的大小。对一个采用确定粒度体系划分的地理区域,第T(T为自然数)级粒度的一个网格由若干个面积相等的第(T+1)级粒度的网格组成。
对一个地理围栏,包含该围栏的最小单一网格即是该围栏的外接网格。换言之,如果在所采用的粒度体系中,某个粒度的一个网格能够涵盖围栏的全部区域,而将该网格划分为下一级粒度后每个更细粒度网格只可能覆盖围栏的部分区域而不可能涵盖全部区域,则该网格即是该围栏的外接网格。
确定围栏外接网格的具体方式可以参照现有技术实现,不再赘述。
步骤120,以外接网格为起点,将包含围栏边界的网格逐层划分为更细粒度的网格,直至划分后网格集合的索引准确率不低于预定精度阈值;网格集合由处于围栏内的网格和包含围栏边界的网格组成,索引准确率为围栏面积与网格集合中所有网格面积之和的比值。
在确定外接网格后,以外接网格作为围栏的索引网格开始进行迭代,此时网格集合中只包括外接网格一个元素。计算网格集合对围栏的索引准确率,如果低于预定精度阈值,则将网格集合中包含围栏边界的网格划分为更细粒度的网格,而对网格集合中处于围栏内部的网格不做处理;如果划分后某个更细粒度的网格完全处在围栏外,则从网格集合中删除该处于围栏外部的网格。重复上述过程直到网格集合对围栏的索引准确率不低于预定精度阈值。
由于外接网格涵盖了围栏的全部区域,并且在迭代过程中,只在网格集合中删除了完全处于围栏外的网格,因此网格集合中的所有网格始终能够涵盖围栏的全部区域,网格集合的索引覆盖率为1。
图2所示为本步骤的一种迭代处理流程的示例,具体步骤如下:
步骤201,生成网格集合,网格集合以处于围栏内的网格和包含围栏边界的网格为元素。此时网格集合中只有外接网格一个元素。
步骤202,以网格集合中的所有网格作为围栏的索引网格,按照式2计算网格集合的索引准确率。比较计算得出的索引准确率和预定精度阈值,如果索引准确率不低于预定精度阈值,则网格集合满足预定精度要求,转步骤210;否则执行步骤203。
步骤203,以网格集合中的第一个网格作为当前网格。
步骤204,判断当前网格是否完全处于围栏内,如果是,转步骤208;如果否,则当前网格为包含围栏边界的网格,执行步骤205。
步骤205,将当前网格划分为下一级更细粒度的网格。具体划分为几个下一级更细粒度的网格,由具体应用场景中所采用的粒度体系决定。
步骤206,在网格集合中,用划分后下一级更细粒度的网格替代当前网格。也即,将当前网格从网格集合中删除,将由当前网格划分而得的若干个下一级更细粒度的网格添加在网格集合中。这些划分后下一级更细粒度的网格中会有包含围栏边界的网格,可能有处于围栏内部的网格,可能有处于围栏外部的网格。
步骤207,如果由网格划分而得的若干个下一级更细粒度的网格中,存在处于围栏外部的网格,由于处于围栏外的网格不会是围栏的索引网格,不应当作为网格集合的元素,因此在网格集合中删除划分后处于围栏外部的下一级网格。如果由网格划分而得的若干个下一级更细粒度的网格中不存在处于围栏外部的网格,则不必进行删除。
步骤208,判断网格集合中是否还有下一个网格,如果有,执行步骤209,继续进行本轮迭代。如果网格集合中没有下一个网格,则本轮迭代处理完毕,网格集合中所有包含围栏边界的网格都已经是更细粒度的网格,转步骤202,通过计算网格集合的索引准确率来判断是否需要进行下一轮次的迭代。
步骤209,将网格集合中的下一个网格作为当前网格,转步骤204。
步骤210,输出网格集合,迭代过程处理完毕。
需要说明的是,图2中的流程只是迭代处理流程的一个例子,可以按照实际应用场景的具体情况以其他的流程来实现迭代过程,本申请的实施例不做限定。
回到图1,步骤130,将网格集合中的网格作为围栏的索引网格。
经过步骤120后,网格集合中所有包含围栏边界的网格都具有相同的粒度,该粒度是网格集合中所有网格粒度中最细的(最为密集的),以下称之为下限粒度。而网格集合中处于围栏内的网格则可能具有不同的粒度,其粒度的可能取值范围是从外接网格粒度的下一级粒度、到下限粒度。
由于网格集合的索引准确率取决于集合中包含围栏边界的网格的粒度,允许集合中处于围栏内的网格采用更大的粒度可以在满足精度要求的前提下,减小索引网格的数量。尤其是步骤120中的迭代过程能够根据围栏的实际形状,尽量采用更粗粒度的网格来覆盖围栏内的面积,在减少索引网格上具有非常好的效果。
将网格集合中的网格作为围栏的索引网格的具体处理方式通常包括在网格集合中每个网格的索引项下登记该围栏对应的实体,也可以根据实际应用场景的需要采用其他方式,不做限定。
在大多数情形下,通过步骤120得到的网格集合,其索引准确率会超过预定精度阈值。当通过步骤120得到的网格集合的索引准确率高于预定精度阈值时,可以将网格集合中的部分网格合并为包含围栏边界的更粗粒度的网格,合并的条件是使合并后的索引准确率不低于预定精度阈值,然后在步骤130中可以将合并后网格集合中的网格作为围栏的索引网格。这样可以进一步减少围栏的索引网格数量。
需要说明的是,网格的合并是指将属于同一个较粗粒度网格的若干个较细网格以该较粗粒度网格代替,而不是取这些较细粒度网格的并集。属于同一个较粗粒度网格的较细粒度网格有可能不都是网格集合中的元素,这种情况下同样可以将网格集合中的一个到多个较细粒度网格合并为该较粗粒度网格。
例如,可以在网格集合中查找由同一个网格划分而得的两个或两个以上、具有下限粒度的网格,将查找到的网格合并为更粗粒度的网格,然后计算合并后网格集合的索引准确率。如果低于预定精度阈值,则停止合并,此时的网格集合为合并后的网格集合。如果不低于预定精度阈值,则在网格集合中将合并后更粗粒度的网格代替合并前的所有网格,然后重复上述过程,查找下一组由同一个网格划分而得的两个或两个以上的网格并判断是否进行合并,直到停止合并。这个例子中的合并方式有可能能够进一步减少索引网格数量,但通常得不出能够最大程度减少网格索引数量的效果。
在一种实现方式中,可以通过背包问题来求解能够最大程度减少网格索引数量的合并方式。背包问题可以描述为:给定一组物品,每种物品都有自己的重量和价格,在限定的总重量内,如何选择才能使得物品的总价最高。在本申请的实施例中,可以将合并后包含围栏边界的网格作为物品,将采用该物品作为索引网格时相比于未合并时增加的围栏外面积作为物品的重量,将采用该物品作为索引网格时相比于未合并时减少的网格数量作为物品的价值,将未合并时网格集合的索引准确率超过预定精度阈值的部分所对应的围栏外面积作为限定总重量,来生成背包问题,将这个背包问题的最优解作为网格合并的结果。将网格合并的结果更新到网格集合中,即可得到合并后的网格集合,例如,可以将网格合并结果中的网格添加到网格集合中,删除与网格合并结果中的网格覆盖相同地理区域的所有原有网格。
在生成背包问题后,可以参照现有技术中背包问题的各种解法得到其最优解,本申请的实施例不做限定。
以下给出一个求解背包问题的具体实现方式。设物品a是一个合并后的网格,物品1和其他网格合并后的网格也可以作为一个物品,设为物品2,则物品2是物品1的父物品,物品1是物品2的子物品。由于物品1和物品2包含有相同的地理区域,当物品1作为网格集合的元素时,物品2必定不是网格集合的元素,反之亦然。也就是说,具有父子关系的物品不能同时存在于一个背包内,具有父子关系的物品包括直接和间接的父子关系,例如,如果物品3是物品2的父物品,则物品1和物品3也不能同时存在于一个背包内。
在求解本实现方式中的背包问题时,可以根据物品间的父子关系构建物品的树形层次结构,然后以具有父子关系的物品不能同时存在于一个背包内作为约束条件,列举背包问题的所有背包状态;求解每种背包状态的答案,所有答案中的最优答案即是背包问题的最优解。
具体而言,可以将下限粒度(即合并前网格集合中最密集网格的粒度)为当前粒度的起点,逐层将网格集合中当前粒度的网格合并为更粗粒度的网格,将每个合并后的网格作为一个物品,确定每个物品的重量和价值,直至将所有网格合并为外接网格。按照物品间的父子关系可以生成物品的树形层次结构,该树形层次结构的叶子结点(即没有后续结点的结点)为由下限粒度的网格合并而成的网格,根结点(即没有前驱结点的结点)为外接网格。
在构建出物品的树形层次结构后,确定作为树形层次结构中叶子结点的每个物品的背包状态。以作为叶子结点的子物品为起点,以父物品的所有子物品的背包状态的笛卡尔积与父物品本身的交集,作为所述父物品的背包状态,直至迭代得出外接网格对应的所述树形层次结构中根结点的背包状态。换言之,采用式3从作为叶子结点的子物品开始,在树形层次结构中逐级向上计算其父物品的背包状态直到计算出根结点的背包状态:
式3中,StateF为父物品的背包状态,NodeF为父物品,为第i个子物品的背包状态,k为父物品的子物品个数。
在迭代计算出作为根结点的父物品,即外接网络的背包状态后,该外接网格的所有背包状态就是背包问题的所有背包状态。每个背包状态都可以看做一个基础背包问题,根据现有技术中基础背包问题的解决办法可以得到每个背包状态的答案,所有背包状态的答案中最优的一个,即为该背包问题的最优解。将本实现方式中背包问题的最优解作为网格集合中网格合并的结果,即可得到在满足预定精度阈值的条件下,该围栏的最少数量的索引网格。
可见,本申请的实施例中,以包含围栏的最小单一网格作为围栏的外接网格,以围栏的外接网格为起点,对包含围栏边界的网格逐层进行更细粒度的划分,直至满足预定精度阈值;通过只增加包含围栏边界的网格的粒度,而不对处于围栏内的网格做进一步的划分,将不同粒度的网格作为索引网格,极大的减少了索引网格的数量,降低了索引存储的复杂度,加快了索引的查询速度。
进一步的,对索引准确度超过预定精度阈值的网格集合,利用背包问题模型来将网格集合中的部分网格合并更粗粒度的网格,通过构建背包问题的树形结构层次来求得最优解,从而在满足索引精度要求的前提下将索引数量降到最低。
在本申请的一个应用示例中,采用图3所示的流程来得到地理围栏的索引网格,要求这些索引网格能够100%覆盖围栏的区域,并且索引准确率不低于预定精度阈值。以下以一个名为Geof-Demo的地理围栏为例进行说明。
步骤310,确定围栏的外接网格。Geof-Demo地理围栏及确定的外接网格如图4所示。
步骤320,以外接网格为元素构成网格集合,将网格集合中包含围栏边界的网格逐层划分为更细粒度的网格,直到划分后网格集合的索引准确率不低于预定精度阈值。
设Geof-Demo所采用的粒度体系为每细化一个粒度,将原有网格划分为4个相等的网格,则从Geof-Demo外接网格开始,前4次划分后网格的分布如图5所示,设经过4次划分后,网格集合的索引准确率超过了预定精度阈值,则划分停止,此时网格集合中的所有元素为图5中灰色背景的网格,其中包含Geof-Demo边界的网格都具有相同的粒度,也是网格集合中所有网格的最细粒度(即下限粒度),而处于Geof-Demo边界内的网格则具有不同的粒度。图5中白色背景的网格为处于围栏外,在划分过程中被从网格集合中删除的网格。
步骤330,判断网格集合的索引准确率等于预定精度阈值,如果相等,则转步骤360;如果索引准确率大于预定精度阈值,执行步骤340。
步骤340,以合并后包含围栏边界的网格作为物品,以该物品作为索引网格时相比于未合并时增加的围栏外面积作为物品的重量,以该物品作为索引网格时相比于未合并时减少的网格数量作为物品的价值,将未合并时网格集合的索引准确率超过预定精度阈值的部分所对应的围栏外面积作为限定总重量,生成背包问题。
从网格集合中具有下限粒度的包含围栏边界的网格开始,逐层合并为更粗粒度的网格,以每个合并后的网格为物品,确定物品的重量和价值。按照合并的层次结构确定物品的父子关系,构建背包问题的树形层次结构。
以图6中右上角所示的具有下限粒度的网格d1、d2、d3、e1、f1、f2和f3为例,d1、d2和d3可以合并为一个更粗粒度的网格,以该网格为物品d;e1可以合并为一个更粗粒度的网格,以该网格为物品e;f1、f2和f3可以合并为一个更粗粒度的网格,以该网格为物品f。将物品d作为索引网格,与网格集合未进行合并时相比,增加的围栏外面积为1个下限粒度网格,减少的索引网格数量为2,可得物品d的重量w=1、价值p=2;类推可得到物品e的重量w=3、价值p=0,物品f的重量w=1、价值p=2。
继续向更粗粒度进行网格的合并,d可以与网格集合中的其他网格合并为一个更粗粒度的网格,以该网格为物品b(图6中以虚线框表示),物品b为物品d的父物品;e和f可以与网格集合中的其他网格合并为一个更粗粒度的网格,以该网格为物品c(图6中以虚线框表示),物品c为物品e、物品f的父物品。将物品b作为索引网格,与网格集合未进行合并时相比,增加的围栏外面积为1个下限粒度网格,减少的索引网格数量为5,可得物品b的重量w=1、价值p=5;类推可得到物品c的重量w=8、价值p=4。物品b和物品c还可以与网格集合中的其他网格合并为一个更粗粒度的网格,以该网格为物品a,物品a的重量w=9、价值p=12。以此类推,直至合并到Geof-Demo的外接网格。
根据合并时物品间的父子关系,可以得到从由下限粒度的网格合并而成的物品(如物品d)、直到外接网格的树形层次结构。以上述物品a到物品f为例,按照合并时物品间的父子关系,可以得到图7所示的树形层次结构。需要说明的是,图7所示的树形层次结构只是Geof-Demo树形层次结构的一个子树。
步骤350,按照物品的树形层次结构,以包含相同地理区域的物品(即具有直接或间接父子关系的物品)不能同时存在于一个背包内作为约束条件,列举背包问题的所有背包状态,求解每个背包状态的答案,以所有答案中的最优解作为网格合并的结果。
以树形层次结构的叶子结点(即由下限粒度的网格合并而得的物品)的状态开始,按照式3进行迭代,直到得到外接网格的状态,即为背包问题的所有背包状态。
以图7所示的子树为例,先确定作为叶子结点的物品d、物品e和物品f的状态:物品d的状态D={d},物品d的状态E={e},物品f的状态F={f}。根据式3计算物品b的状态B=b+D={{b},{d}},物品c的状态F={c,{e,f}}。再计算物品a的状态继续类推可以得到外接网格的状态。
每一个外接网格的状态是一个基础背包问题,可按照现有技术得到其答案。取所有状态的答案中最优的一个,作为网格合并的结果。按照网格合并的结果更新网格集合。
步骤360,以网格集合中的网格作为围栏的索引网格。Geof-Demo最终的网格集合中的网格如图8所示。
在将本应用示例中的方法应用于实践后,与现有技术中采用单一粒度索引网格相比,取得了显著的效果。以包括写字楼、小区、商场、机场、医院等围栏的地理区域为对象,对比结果如表1所示:
表1
可见,在准确率更高的情况下,本应用示例的索引数量比单一粒度索引网格减少了30多倍。更高的索引准确率,使围栏服务的位置判断更加精准,提高服务效果并且降低打扰率;更少的索引数量,使索引数据占用的存储空间更小,从而提高服务建设所依赖的环境,提高服务的鲁棒性和灵活性。
与上述流程实现对应,本申请的实施例还提供了一种确定地理围栏的索引网格的装置。该装置均可以通过软件实现,也可以通过硬件或者软硬件结合的方式实现。以软件实现为例,作为逻辑意义上的装置,是通过所在设备的CPU(Central Process Unit,中央处理器)将对应的计算机程序指令读取到内存中运行形成的。从硬件层面而言,除了图9所示的CPU、内存以及存储器之外,确定地理围栏的索引网格的装置所在的设备通常还包括用于进行无线信号收发的芯片等其他硬件,和/或用于实现网络通信功能的板卡等其他硬件。
图10所示为本申请实施例提供的一种确定地理围栏的索引网格的装置,包括外接网格单元、网格划分单元和索引确定单元,其中:外接网格单元用于确定围栏的外接网格,所述外接网格为包含围栏的最小单一网格;网格划分单元用于以外接网格为起点,将包含围栏边界的网格逐层划分为更细粒度的网格,直至划分后网格集合的索引准确率不低于预定精度阈值;所述网格集合由处于围栏内的网格和包含围栏边界的网格组成,所述索引准确率为围栏面积与网格集合中所有网格面积之和的比值;索引确定单元用于将网格集合中的网格作为所述围栏的索引网格。
一种实现方式中,所述装置还包括:网格合并单元,用于在网格集合的索引准确率高于预定精度阈值时,将网格集合中的部分网格合并为包含围栏边界的更粗粒度的网格,使合并后的索引准确率不低于预定精度阈值;所述索引确定单元具体用于:将合并后网格集合中的网格作为所述围栏的索引网格。
上述实现方式中,所述网格合并单元将网格集合中的部分网格合并为包含围栏边界的更粗粒度的网格,使合并后的索引准确率不低于预定精度阈值,包括:将合并后包含围栏边界的网格作为物品,将采用所述物品作为索引网格时相比于未合并时增加的围栏外面积作为物品的重量,将采用所述物品作为索引网格时相比于未合并时减少的网格数量作为物品的价值,将未合并时网格集合的索引准确率超过预定精度阈值的部分所对应的围栏外面积作为限定总重量,生成背包问题,将所述背包问题的最优解作为网格合并的结果;所述索引确定单元具体用于:按照网格合并的结果更新网格集合,将更新后网格集合中的网格作为所述围栏的索引网格。
一个例子中,所述网格合并单元将背包问题的最优解作为网格合并的结果,包括:构建所述背包问题物品的树形层次结构,所述树形层次结构中父物品由其子物品合并而成;以具有父子关系的物品不能同时存在于一个背包内作为约束条件,列举所述背包问题的所有背包状态;求解每种背包状态的答案,以所有答案中的最优答案作为所述背包问题的最优解。
上述例子中,所述网格合并单元构建背包问题物品的树形层次结构,包括:以下限粒度为当前粒度的起点,逐层将网格集合中当前粒度的网格合并为更粗粒度的网格,并以每个合并后的网格为一个物品,确定所述物品的重量和价值,直至将所有网格合并为外接网格;按照物品间的父子关系生成物品的树形层次结构;所述下限粒度为合并前网格集合中最密集网格的粒度。
上述例子中,所述网格合并单元以具有父子关系的物品不能同时存在于一个背包内作为约束条件,列举所述背包问题的所有背包状态,包括:确定作为所述树形层次结构中叶子结点的每个物品的背包状态;以作为叶子结点的子物品为起点,以父物品的所有子物品的背包状态的笛卡尔积与父物品本身的交集作为所述父物品的背包状态,直至迭代得出所述树形层次结构中根结点对应的外接网格的背包状态,即为所述背包问题的所有背包状态。
本申请的实施例提供了一种计算机设备,该计算机设备包括存储器和处理器。其中,存储器上存储有能够由处理器运行的计算机程序;处理器在运行存储的计算机程序时,执行本申请实施例中确定地理围栏的索引网格的方法的各个步骤。对确定地理围栏的索引网格的方法的各个步骤的详细描述请参见之前的内容,不再重复。
本申请的实施例提供了一种计算机可读存储介质,该存储介质上存储有计算机程序,这些计算机程序在被处理器运行时,执行本申请实施例中确定地理围栏的索引网格的方法的各个步骤。对确定地理围栏的索引网格的方法的各个步骤的详细描述请参见之前的内容,不再重复。
以上所述仅为本申请的较佳实施例而已,并不用以限制本申请,凡在本申请的精神和原则之内,所做的任何修改、等同替换、改进等,均应包含在本申请保护的范围之内。
在一个典型的配置中,计算设备包括一个或多个处理器(CPU)、输入/输出接口、网络接口和内存。
内存可能包括计算机可读介质中的非永久性存储器,随机存取存储器(RAM)和/或非易失性内存等形式,如只读存储器(ROM)或闪存(flash RAM)。内存是计算机可读介质的示例。
计算机可读介质包括永久性和非永久性、可移动和非可移动媒体可以由任何方法或技术来实现信息存储。信息可以是计算机可读指令、数据结构、程序的模块或其他数据。计算机的存储介质的例子包括,但不限于相变内存(PRAM)、静态随机存取存储器(SRAM)、动态随机存取存储器(DRAM)、其他类型的随机存取存储器(RAM)、只读存储器(ROM)、电可擦除可编程只读存储器(EEPROM)、快闪记忆体或其他内存技术、只读光盘只读存储器(CD-ROM)、数字多功能光盘(DVD)或其他光学存储、磁盒式磁带,磁带磁磁盘存储或其他磁性存储设备或任何其他非传输介质,可用于存储可以被计算设备访问的信息。按照本文中的界定,计算机可读介质不包括暂存电脑可读媒体(transitory media),如调制的数据信号和载波。
还需要说明的是,术语“包括”、“包含”或者其任何其他变体意在涵盖非排他性的包含,从而使得包括一系列要素的过程、方法、商品或者设备不仅包括那些要素,而且还包括没有明确列出的其他要素,或者是还包括为这种过程、方法、商品或者设备所固有的要素。在没有更多限制的情况下,由语句“包括一个……”限定的要素,并不排除在包括所述要素的过程、方法、商品或者设备中还存在另外的相同要素。
本领域技术人员应明白,本申请的实施例可提供为方法、系统或计算机程序产品。因此,本申请可采用完全硬件实施例、完全软件实施例或结合软件和硬件方面的实施例的形式。而且,本申请可采用在一个或多个其中包含有计算机可用程序代码的计算机可用存储介质(包括但不限于磁盘存储器、CD-ROM、光学存储器等)上实施的计算机程序产品的形式。