《一种序列号的处理方法及设备.pdf》由会员分享,可在线阅读,更多相关《一种序列号的处理方法及设备.pdf(15页珍藏版)》请在专利查询网上搜索。
1、(10)申请公布号 CN 103164418 A(43)申请公布日 2013.06.19CN103164418A*CN103164418A*(21)申请号 201110412749.3(22)申请日 2011.12.12G06F 17/30(2006.01)(71)申请人阿里巴巴集团控股有限公司地址英属开曼群岛大开曼岛资本大厦一座四层847号邮箱(72)发明人谢智永(74)专利代理机构北京同达信恒知识产权代理有限公司 11291代理人郭润湘(54) 发明名称一种序列号的处理方法及设备(57) 摘要本申请提出一种序列号的处理方法及设备,当服务器需要向数据库中写入数据记录时,按照设定的数据库查询顺。
2、序,从多个数据库中选择一个数据库,读取选择的数据库中的序列表,以及从读取的序列表中获取N个可用序列号,并使用可用序列号将所述数据记录写入数据库中。由于服务器可以按查询顺序从多个数据库中选择一个数据库的序列表来获取序列号,并不局限于某一个数据库中序列表来获取序列号,有效的弱化了序列表和数据库之间的依赖关系,实现了序列号的共享,即使出现某一数据库中的序列号耗尽或数据库故障的情况,服务器仍然可以从其他数据库中获取序列号,克服了由于部分数据库中的序列号耗尽后,就无法向该数据库继续写入数据记录的问题。(51)Int.Cl.权利要求书3页 说明书9页 附图2页(19)中华人民共和国国家知识产权局(12)发。
3、明专利申请权利要求书3页 说明书9页 附图2页(10)申请公布号 CN 103164418 ACN 103164418 A1/3页21.一种序列号的处理方法,其特征在于,包括:服务器在需要向数据库中写入数据记录时,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,并读取选择的数据库中的序列表;服务器从读取的序列表中获取N个可用序列号,所述N为正整数;服务器根据获取的可用序列号将所述数据记录写入数据库中。2.如权利要求1所述的序列号的处理方法,其特征在于,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,具体包括:若服务器首次向数据库中写入数据记录,则从所述多个数据库中随机选择一个数。
4、据库;若服务器不是首次向数据库中写入数据记录,则确定上一次选择的数据库,并根据所述数据库查询顺序,确定当前选择的数据库。3.如权利要求1所述的序列号的处理方法,其特征在于,在服务器需向数据库中写入数据记录之前,所述方法还包括:为所述多个数据库中的每个数据库按照标号从小到大的顺序依次设置标号;针对任一数据库中的序列表,通过以下方式生成序列表中的序列号:将数据库的标号作为该数据库中序列表的初始序列号,并判断所述多个数据库的数量D是否为2的指数倍,所述D为大于1的正整数;若是,针对任一数据库中的序列表,将该序列表中的初始序列号依次以D为增长步长得到的序列号作为该序列表中的序列号;若否,确定小于D且距。
5、离D最近的2的指数倍数值X;针对标号不小于D-X且小于X的数据库中的序列表,将该序列表中的初始序列号依次以X为增长步长得到的序列号作为该序列表中的序列号;针对剩余数据库中的序列表,将该序列表中的初始序列号依次以2X为增长步长得到的序列号作为该序列表中的序列号。4.如权利要求3所述的序列号的处理方法,其特征在于,所述方法还包括:当任一数据库需要拆分为K个子数据库时,所述数据库中的序列表也拆分为K个子序列表,所述K为大于1的正整数;其中:所述K个子序列表中的任一子序列表的初始序列号为:拆分前序列表中可用的最小K个序列号中的一个序列号,且任意两个子序列表的初始序列号不相同,任一子序列表中序列号间的增。
6、长步长为拆分前序列表中序列号间步长的K倍。5.如权利要求3所述的序列号的处理方法,其特征在于,服务器通过以下方式获取N个可用序列号:服务器读取选择的数据库中序列表的下一可用序列号Current_next_value;服务器根据以下公式更新读取的Current_next_value:Current_next_value_newCurrent_next_value+increase_stepN其中,Current_next_value_new为更新后的下一可用序列号,increase_step为增长步长,N为序列表中从Current_next_value起连续获取的序列号的个数;服务器判断Curr。
7、ent_next_value_new是否能够回写至序列表中;若是,则将所述Current_next_value_new回写至序列表,并将从序列表中读取的从权 利 要 求 书CN 103164418 A2/3页3Current_next_value起连续的N个序列号为获取的N个可用的序列号;若否,服务器按照数据库查询顺序读取下一个数据库中序列表的Current_next_value,并重复执行根据所述公式得到Current_next_value_new,以及判断Current_next_value_new是否能够回写至序列表的操作。6.如权利要求1所述的序列号的处理方法,其特征在于,所述方法还包。
8、括:服务器再次需要向数据库中写入数据记录时,判断已获取的N个可用序列号是否都已使用过;若是,则重新执行按照设定的数据库查询顺序,从多个数据库中选择一个数据库的操作;若否,从所述已获取的N个可用序列号中选择还没有使用过的可用序列号,并根据选择的所述可用序列号将数据记录写入数据库中。7.一种序列号的处理设备,其特征在于,包括:选择模块,用于在需要向数据库中写入数据记录时,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,并读取选择的数据库中的序列表;获取模块,用于从读取的序列表中获取N个可用序列号,所述N为正整数;写入模块,用于根据获取的可用序列号将所述数据记录写入数据库中。8.如权利要求7。
9、所述的序列号的处理设备,其特征在于,所述选择模块,具体包括:第一选择单元,用于若首次向数据库中写入数据记录,则从所述多个数据库中随机选择一个数据库;第二选择单元,用于若不是首次向数据库中写入数据记录,则确定上一次选择的数据库,并根据所述数据库查询顺序,确定当前选择的数据库。9.如权利要求7所述的序列号的处理设备,其特征在于,所述设备还包括:标号设置模块,用于为所述多个数据库中的每个数据库按照标号从小到大的顺序依次设置标号;序列号生成模块,用于针对任一数据库中的序列表,通过以下方式生成序列表中的序列号:将数据库的标号作为该数据库中序列表的初始序列号,并判断所述多个数据库的数量D是否为2的指数倍,。
10、所述D为大于1的正整数;若是,针对任一数据库中的序列表,将该序列表中的初始序列号依次以D为增长步长得到的序列号作为该序列表中的序列号;若否,确定小于D且距离D最近的2的指数倍数值X;针对标号不小于D-X且小于X的数据库中的序列表,将该序列表中的初始序列号依次以X为增长步长得到的序列号作为该序列表中的序列号;针对剩余数据库中的序列表,将该序列表中的初始序列号依次以2X为增长步长得到的序列号作为该序列表中的序列号。10.如权利要求9所述的序列号的处理设备,其特征在于,所述设备还包括:拆分模块,用于当任一数据库需要拆分为K个子数据库时,所述数据库中的序列表也拆分为K个子序列表,所述K为大于1的正整数。
11、;其中:所述K个子序列表中的任一子序列表的初始序列号为:拆分前序列表中可用的权 利 要 求 书CN 103164418 A3/3页4最小K个序列号中的一个序列号,且任意两个子序列表的初始序列号不相同,任一子序列表中序列号间的增长步长为拆分前序列表中序列号间步长的K倍。权 利 要 求 书CN 103164418 A1/9页5一种序列号的处理方法及设备技术领域0001 本申请涉及计算机技术领域,尤其涉及一种序列号的处理方法及设备。背景技术0002 序列表是用于创建唯一连续整数值的数据库对象,其典型的用途是创建全局唯一的序列号,以标识数据表中的一条数据记录。在数据表中的数据记录条数较少时,可直接在存。
12、放该数据表的数据库中创建一张序列表,在新增数据记录时,服务器从该序列表中获取序列号,并利用该序列号标识新增的数据记录。0003 若数据库中需要记录的数据记录数量达到或超过一定规模后(如1000万),随着数据记录条数的继续增加,如果所有的数据记录都记录在同一数据表中,则对该数据表中的数据记录进行读、写操作的性能将会明显下降。因此,可将数据记录记载在多个数据表中,并将多个数据表存放于一个或多个数据库中,且为每个数据记录分配一个序列号。具体地,当有一个新增的数据记录需要写入数据库时,从序列表中获取一个序列号分配给当前新增的数据记录,完成数据记录的写入操作。0004 具体地,从序列表中获取分配给数据记。
13、录的序列号的方式包括以下两种:0005 第一种方式:0006 在存储数据表的多个数据库中选择一个数据库,用于建立并存储序列表,所述序列表中有一个设定字段。当服务器需要获取序列号向数据库中写入数据记录时,从所述序列表中获取一个可用的序列号。0007 在第一种序列号的获取方式下,存在单点风险,即当负责建立并存储序列表的数据库出现故障时,序列号的获取操作将无从进行,导致数据记录的写入操作也将无法进行。0008 第二种方式:0009 分别在每个数据库中建立一张序列表,并为该序列表分配一段序列号区间,在系统运行时,当服务器需要向某一数据库中写入数据记录时,则从该数据库中的序列表中获取序列号,也就是说,一。
14、个数据库中序列表内的序列号分配给同一数据库中的数据记录。0010 在第二种序列号的获取方式下,可以避免单点风险,但由于为每个数据库分配了固定的序列号区间,这些序列号只能分配给同一数据库中的数据记录,因此,可能会出现部分数据库中的序列号耗尽,但部分数据库中序列号使用率较低的情况。0011 另外,在对数据库进行扩展时,可能需要将一个数据库拆分为多个数据库,同时也要将拆分前数据库的序列表拆分为多个,此时,若在拆分前序列表中的部分序列号已被使用过,则可能导致拆分后的序列表无法合理分配给各拆分后的数据库。0012 例如:数据库1的序列表1中的序列号为0999,其中,0300的序列号已被使用过,则数据库1。
15、被拆分为数据库11和数据库12时,若序列表1也拆分为序列表11和序列表12,且序列表11中的序列号为0499,序列表12中的序列号为500999,则由于序列表11中的部分序列号已被使用过,导致数据库的扩展效果较差。说 明 书CN 103164418 A2/9页6发明内容0013 本申请实施例提供一种序列号的处理方法及设备,用以解决现有技术中由于部分数据库中的序列号耗尽后,就无法向该数据库继续写入数据记录的问题。0014 一种序列号的处理方法,包括:0015 服务器在需要向数据库中写入数据记录时,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,并读取选择的数据库中的序列表;0016 服务。
16、器从读取的序列表中获取N个可用序列号,所述N为正整数;0017 服务器根据获取的可用序列号将所述数据记录写入数据库中。0018 一种序列号的处理设备,包括:0019 选择模块,用于在需要向数据库中写入数据记录时,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,并读取选择的数据库中的序列表;0020 获取模块,用于从读取的序列表中获取N个可用序列号,所述N为正整数;0021 写入模块,用于根据获取的可用序列号将所述数据记录写入数据库中。0022 本申请有益效果如下:0023 在本申请实施例提供的方案中,当服务器需要向数据库中写入数据记录时,由于服务器可以按查询顺序从多个数据库中选择一个数。
17、据库的序列表来获取序列号,并不局限于某一个数据库中序列表来获取序列号,有效的弱化了序列表和数据库之间的依赖关系,实现了序列号的共享,即使出现某一数据库中的序列号耗尽或数据库故障的情况,服务器仍然可以从其他数据库中获取序列号,克服了由于部分数据库中的序列号耗尽后,就无法向该数据库继续写入数据记录的问题。附图说明0024 图1为本申请实施例一序列号的处理方法步骤示意图;0025 图2为本申请实施例二序列号的处理方法步骤示意图;0026 图3为本申请实施例三序列号的处理设备结构示意图。具体实施方式0027 为实现本申请目的,本申请实施例提出一种序列号的处理方案,当服务器需要向数据库中写入数据记录时,。
18、按照设定的数据库查询顺序,从多个数据库中选择一个数据库,读取选择的数据库中的序列表,以及从读取的序列表中获取N(N为正整数)个可用序列号,并使用可用序列号将所述数据记录写入数据库中。由于服务器可以按查询顺序从多个数据库中选择一个数据库的序列表来获取序列号,并不局限于某一个数据库中序列表来获取序列号,有效的弱化了序列表和数据库之间的依赖关系,实现了序列号的共享,即使出现某一数据库中的序列号耗尽或数据库故障的情况,服务器仍然可以从其他数据库中获取序列号,克服了由于部分数据库中的序列号耗尽后,就无法向该数据库继续写入数据记录的问题。0028 下面结合说明书附图对本申请实施例的方案进行详细描述。002。
19、9 实施例一0030 如图1所示,其为本申请实施例一中序列号的处理方法步骤示意图,所述方法包说 明 书CN 103164418 A3/9页7括以下步骤:0031 步骤101:服务器在需要向数据库中写入数据记录时,按照设定的数据库查询顺序,从多个数据库中选择一个数据库,并读取选择的数据库中的序列表。0032 通常情况下,一个数据库架构中可以包含多个服务器和多个数据库,任一一个服务器可以对属于同一数据库架构中的各数据库进行数据记录的查询、写入、删除等操作;较优的,考虑到在实际过程中,当业务系统启动时,可能会出现多个服务器同时从某一数据库的序列表中获取序列号的情况,会造成序列号抢占冲突,为了降低出现。
20、序列号抢占冲突的概率,服务器按照设定的数据库查询顺序,从多个数据库中选择一个数据库的方式具体可以为:0033 若服务器首次向数据库中写入数据记录,则从所述多个数据库中随机选择一个数据库;0034 若服务器不是首次向数据库中写入数据记录,则确定上一次选择的数据库,并根据所述数据库查询顺序,确定当前选择的数据库,例如:将数据库按照命名或其他方式进行排列,在确定上一次选择的数据库后,将与上一次选择的数据库相邻的下一数据库作为当前选择的数据库,若上一次选择的是排列在最后的一个数据库,则可将排列在第一位的数据库作为当前选择的数据库。0035 所述首次向数据库中写入数据记录是指,业务系统启动后,服务器上电。
21、后第一次执行数据记录写入操作。0036 在本步骤101的方案中,服务器在需要向任一数据库中写入数据记录时,都可以按照本步骤101的方案执行。0037 本实施例中的序列表是在创建数据库时,利用诸如数据库结构化查询语言(SQL)等计算机语言创建的。序列表可以用来存放序列号以及序列号的生成信息,在服务器对数据库进行一条数据记录的写入操作时,需要从序列表中获取一个序列号,以标识该条数据记录。0038 在本实施例的方案中,包括但不限于以下三种方式在序列表中生成序列号:0039 第一种方式:0040 根据为每个数据库中设置的标号来确定数据库中序列表的初始序列号,进而按照一定的增长步长增长同一序列表中的其他。
22、序列号,具体可以为:0041 第一步,按照标号从小到大的顺序,依次为各数据库设置标号。0042 第二步,将数据库的标号作为该数据库中序列表的初始序列号,并判断所述多个数据库的数量D是否为2的指数倍,所述D为大于1的正整数,若是,则执行第三步,若否,则执行第四步。0043 第三步,针对任一数据库中的序列表,将该序列表中的初始序列号依次以D为增长步长,得到的序列号与该初始序列号一起作为该序列表中的序列号,此时,完成序列号的生成操作。0044 第四步,确定小于D且距离D最近的2的指数倍数值X。0045 第五步,针对标号不小于D-X且小于X的数据库中的序列表,将该序列表中的初始序列号依次以X为增长步长。
23、,得到的序列号作为该序列表中的序列号;针对剩余数据库中的序列表,将该序列表中的初始序列号依次以2X为增长步长,得到的序列号作为该序列表说 明 书CN 103164418 A4/9页8中的序列号。0046 例如,假设数据库数目D为4,也就是数据库的数量D是2的指数倍的情况,此时,可设定各数据库标号为0、1、2、3,各数据库中序列表的初始序列号分别为0、1、2、3。针对标号为0的数据库,其中序列表的初始序列号为0,并以4为增长步长,得到的序列号4、8、12、16、.与0一起作为标号为0的数据库中序列表的序列号。针对其他数据库中序列表的序列号生成过程类似。0047 再例如,假设数据库数目D为5,也就。
24、是数据库的数量D不是2的指数倍的情况,此时,仍可设定各数据库标号为0、1、2、3、4,各数据库中序列表的初始序列号分别为0、1、2、3、4。与5最接近的2的指数倍数值X为4。0048 标号不小于D-X且小于X的数据库为数据库1、数据库2和数据库3,以数据库1为例,该数据库1中初始序列号为1,并以4为增长步长,得到的序列号5、9、13、17、.与1一起作为标号为1的数据库中序列表的序列号;针对数据库2和数据库3,其做法与针对数据库1的做法相同。0049 剩余的标号为0和4的数据库,以标号为0的数据库为例,该数据库0中初始序列号为0,并以8为增长步长,得到的序列号8、16、24、32、.与0一起作。
25、为标号为0的数据库中序列表的序列号;针对数据库4,其做法与针对数据库0的做法相同。0050 需要说明的是,在第一种方式下,数据库的标号是默认从0开始依次增加1的数字命名方式来设定的,本实施例也不限于其他利用数字命名方式(如从1开始)来为数据库设定标号。0051 通过上述第一种方式,由于是针对2的指数倍数值来确定增长步长,因此,可简便地实现对数据库以及数据库中序列表的拆分。0052 例如,当某一数据库需要拆分为K个子数据库时,所述数据库中的序列表也可拆分为K个子序列表,其中:所述K个子序列表中的任一子序列表的初始序列号为:拆分前序列表中可用的最小K个序列号中的一个序列号,且任意两个子序列表的初始。
26、序列号不相同,同时,任一子序列表中序列号间的增长步长为拆分前序列表中序列号间步长的K倍。0053 例如,假设拆分前数据库1中序列表1的序列号分别为0、4、8、12、16、20、.,其初始序列号为0,增长步长为4。当该数据库1拆分为数据库11和数据库12时,针对数据库11的序列表11中序列号为:0、8、16、24、.,其初始序列号为0,步长为8;针对数据库12的序列表12中序列号为:4、12、20、28.,其初始序列号为4,步长为8。0054 第二种方式:0055 第一步,按照标号从小到大的顺序,依次为各数据库设置标号。0056 第二步,将数据库的标号作为该数据库中序列表的初始序列号。0057 。
27、第三步,针对任一序列表,将该序列表中的初始序列号依次以D为增长步长,得到的序列号作为该序列表中的序列号。0058 例如,假设数据库的数目D为5,设定各数据库标号为0、1、2、3、4,各数据库中序列表的初始序列号分别为0、1、2、3、4。针对标号为0的数据库,其中序列表的初始序列号为0,并以5为增长步长,得到的序列号5、10、15、20、.与0一起作为标号为0的数据库中序列表的序列号。针对其他数据库中序列表的序列号生成过程类似。0059 第三种方式:说 明 书CN 103164418 A5/9页90060 为各数据库中的序列表设定序列号区间。0061 步骤102:服务器从读取的序列表中获取N个可。
28、用序列号,所述N为正整数。0062 本步骤102的具体实现方式包括但不限于以下两种方式:0063 第一种方式:0064 服务器从数据库的序列表中查找还没有使用过的序列号,并从还没有使用过的序列号中选择N个序列号作为本步骤102中的N个可用序列号。0065 第二种方式:0066 为了避免多个服务器从同一数据库中同时获取序列号导致抢占冲突的问题,第二种方式对第一种方式进行优化,具体如下:0067 第一步,服务器读取选择的数据库中序列表的下一可用序列号Current_next_value。0068 在本实施例的方案,服务器每当从序列表中获取N个序列号后,可将该序列表中与本次获取的N个序列号中最后一个。
29、序列号相邻的下一个没有使用过的序列号作为Current_next_value。0069 例如,某一序列表中序列号为:0、4、8、12、16、20、.,服务器某次获取的4个序列号为0、4、8、12,则将16作为Current_next_value回写至该序列表中。0070 第二步,服务器根据公式(1)更新读取的Current_next_value:0071 Current_next_value_newCurrent_next_value+increase_stepN (1)0072 其中,Current_next_value_new为更新后的下一可用序列号,increase_step为增长步长,。
30、N为序列表中从Current_next_value起连续获取的序列号的个数。0073 第三步,服务器判断Current_next_value_new是否能够回写至序列表中,若是,则执行第四步;若否,则执行第五步。0074 由于可能出现多个服务器同时从同一数据库获取序列号的情况,因此,当服务器1将Current_next_value_new回写至序列表时,若已有其他服务器2抢先从该数据库获取了序列表,也就是说,服务器2已先于服务器1按照上述公式(1)计算出Current_next_value_new并回写至序列表中,因此,服务器1将无法再次写入相同内容或是数值较小的Current_next_va。
31、lue_new;若此时没有其他服务器2抢先获取序列表,则服务器1根据公式(1)计算出的Current_next_value_new大于序列表中当前已存储的Current_next_value,因此,服务器1可从该序列表中获取可用的序列号。0075 第四步,服务器将所述Current_next_value_new回写至序列表,此时,序列表中的Current_next_value的内容更新为Current_next_value_new的内容,并将从序列表中读取的从Current_next_value起连续的N个序列号作为获取的N个可用的序列号。0076 例如,某一序列表中序列号增长步长为4,内容分。
32、别为:0、4、8、12、16、20、24、28、32、.,服务器每次获取的序列号数量N为4。若在第一步获取的某次获取的Current_next_value为16,则通过公式(1)计算出的Current_next_value_new为32,此时,该Current_next_value_new为32的值能够回写至序列表,服务器可将16、20、24、28作为获取的4个可用的序列号。0077 第五步,服务器按照数据库查询顺序读取下一个数据库,并针对所述下一个数据库跳转重新开始执行第一步,直至获取N个可用的序列号。说 明 书CN 103164418 A6/9页100078 步骤103:服务器根据获取的可。
33、用序列号将所述数据记录写入数据库中。0079 步骤104:服务器再次需要向数据库中写入数据记录时,判断已获取的N个可用序列号是否都已使用过,若是,则执行步骤105;若否,则执行步骤106。0080 步骤105:重新执行按照设定的数据库查询顺序,跳转至步骤101。0081 步骤106:从所述已获取的N个可用序列号中选择还没有使用过的可用序列号,并根据选择的所述可用序列号将数据记录写入数据库中。0082 本实施例方案应用在SQL数据库系统、Oracel数据库系统或其他数据库系统中,可以但不局限于利用SQL语言来实现。0083 实施例二0084 考虑到服务器在获取序列号时的避免抢占冲突及确保各服务器。
34、获取的序列号的唯一性,确保数据库的一致性和完整性,本实施例二结合锁技术来详细描述本实施例一的优选实现方案。0085 如图2所示,其为本申请实施例二中序列号的处理方法步骤示意图,所述方法包括以下步骤:0086 步骤201:服务器获取同步锁。0087 所述同步锁锁定的粒度为数据组表。0088 所述数据组表为所述多个数据库中的每个数据库中记录同一业务的数据表的总称,组成数据组表的数据表中的每条数据记录均需获得全局唯一的可用序列号。0089 在本步骤201中获取同步锁可避免多个服务器发起的请求并发问题,在一个时间点只允许一个线程尝试获取一个数据库中的序列号。0090 较优的,本方案若用编程来实现,则其。
35、核心数据结构可以为下述形式:0091 table_group_name/需要使用全局唯一序列号的数据组表的名称,每个分0092 /组之间相互独立,相同table_group_name的序列表记0093 /录负责维护同一组数据表的序列号,该序列号字段在0094 /序列表中需要确保唯一性0095 current_next_value/当前下一个有效的值,每次程序申领序列号时,都会0096 /将本批有效序列号的最大值的下一个有效值更新到0097 /current_next_value中0098 increase_step /每个序列号增长的步长,在本申请的实施例中其值为0099 /X或2X0100 。
36、take_patch/系统每次批量获取的有效序列号的个数,在本申请的0101 /实施例中其值为N0102 步骤202:服务器判断本地是否有可用序列号,若是,则利用该可用序列号进行数据记录的写入操作,否则,执行步骤203。0103 若本步骤202是服务器上首次发出的获取可用序列号的请求,则可按照实施例一中步骤102的方式从随机选择的数据库中获取N个可用序列号;否则,服务器判断上一次从数据库中获取的N个可用序列号是否已用尽,若是,则执行步骤203,继续从数据库中获取N个可用序列号,否则,直接使用本地已存储的还没有使用过的可用序列号。0104 步骤203:服务器等待发出获取可用序列号的请求。说 明 书CN 103164418 A10。