Postgresql - Index Access Method Interface Definition 索引访问方法接口定义(二)

来看一下官方文档是如何定义索引访问方法的

Index Access Method Functions
IndexAmRoutine 索引访问方法必须提供的索引构造和维护功能
建立一个新的索引。索引relation已经被物理创建,但是是空的。它必须用访问方法所需的任何固定数据来填充,再加上表中已经存在的所有元组的条目。通常,ambuild函数将调用IndexBuildHeapScan()来扫描表中现有元组,并计算需要插入索引的键。函数必须返回一个包含关于新索引的统计数据的palloc'd结构。
建立一个空索引,并将其写入给定关系的初始化分叉(INIT_FORKNUM)。此方法仅用于未记录索引;写入初始化叉的空索引将在每个服务器重新启动时在主关系分叉上复制。
将新元组插入现有索引中。值和null数组给出索引的索引值, heap_tid 是索引的TID。如果访问方法支持唯一索引(其amcanunique标志为TRUE),则检查唯一性指示要执行的唯一性检查的类型。这取决于唯一约束是否可推迟。通常,访问方法在执行唯一性检查时只需要heapRelation参数。函数的布尔值只有当检查唯一是UNIQUE_CHECK_PARTIAL时才有意义。在这种情况下,真正的结果意味着新的条目是已知的唯一的,而false意味着它可能是非唯一的。对于其他情况,推荐一个恒定的假结果。有些索引可能不索引所有元组。如果元组不被索引,那么aminsert应该只返回而不做任何事情。
如果索引AM希望通过SQL语句中的连续索引插入来缓存数据,它可以在indexInfo->ii_Context 中分配空间,并将指针存储到 indexInfo->ii_AmCache中的数据(初始为空)。
从索引中删除元组。这是一个“批量删除”操作,旨在通过扫描整个索引并检查每个条目来查看是否应该删除它。必须调用传入的回调函数,在样式回调(TID,callback_state)中返回BOOL,以确定是否将被引用的TID标识的任何特定索引条目删除。必须返回 NULL 或 a palloc'd结构,其中包含有关删除操作的影响的统计信息。如果没有需要传递到amvacuumcleanup的信息,返回null是可以的。
在vacuum操作后清理(零或更多AdvkDelphi调用)。除了返回索引统计信息之外,这不需要做任何事情,但是它可以执行批量清理,例如回收空索引页。STATS是返回的最后一个AdvkDelk调用的任何一个,或者如果没有调用AdkDebug,因为没有必要删除元组。如果结果不是NULL,它必须是一个Palc结构。它所包含的统计信息将用于更新PGSH类,如果给出冗长的话,将通过真空报告。如果在真空操作期间索引没有完全改变,返回null是可以的,但是应该返回正确的统计数据。
将在完成分析操作时调用amvacuumcleanup。在这种情况下,STATS总是NULL,任何返回值都将被忽略。这种情况可以通过检查 info->analyze_only来区分。建议访问方法除了在这种调用中进行后插入清除之外,在autovacuum工作过程中不做任何事情。
通过索引的索引项返回索引列值,检查索引是否可以支持对给定列的仅索引扫描。属性号为1,即第一列的attno为1。如果支持,则返回true,否则为false。如果访问方法根本不支持仅索引扫描,则其索引amcanreturn中的IndexAmRoutine字段可以设置为NULL。
分析和验证索引的reloptions数组。只有当该索引存在非空的reloptions数组时才调用。reloptions是包含表单name=value的条目的文本数组。函数应该构造一个bytea值,该值将被复制到索引的relcache条目的rd_options字段中。bytea值的数据内容对于访问方法是开放的;大多数标准访问方法都使用StdRdOptions。当验证为真时,如果任何选项不被识别或具有无效值,则函数应报告一个合适的错误消息;当验证为false时,应忽略无效的条目。(在加载已存储在pg_catalog目录中的选项时,验证是错误的;如果访问方法更改了其选项的规则,只能找到无效的条目,在这种情况下,忽略过时的条目是适当的。)如果需要默认行为,返回NULL是可以的。
amproperty方法允许索引访问方法重写pg_index_column_has_property和相关函数的默认行为。如果访问方法没有用于索引属性查询的任何特殊行为,则其IndexAmRoutine结构中的amproperty字段可以设置为NULL。否则,amproperty方法将被调用index_oid valid 和 attno 调用,而对于pg_index_has_property调用,则使用 index_oid valid 和 attno调用为零,或者pg_index_has_property调用为零,或者对于pg_index_column_has_property调用具有index_oid valid 和 attno 大于0。prop是一个枚举值,它标识正在测试的属性,而propname是原始属性名称字符串。访问方法可以通过检查匹配的propname来定义自定义属性名称(使用pg_strcasecmp匹配,以与核心代码一致);对于核心代码已知的名称,最好检查prop。如果amproperty方法返回true,则它已确定属性测试结果:它必须将 *res 设置为返回布尔值,或者将 *isnull 设置为TRUE以返回NULL。(两个引用的变量在调用之前被初始化为false)如果amproperty方法返回false,则核心代码将继续其正常逻辑来确定属性测试结果。
支持排序操作符的访问方法应该实现AMPROP_DISTANCE_ORDERABLE属性测试,因为核心代码不知道如何做到这一点,并且将返回null。如果可以通过打开索引和调用AMPROP_RETURNABLE(这是核心代码的默认行为),那么实现amcanreturn测试也可能是有利的。默认行为应该对所有其他标准属性都是满意的。
验证访问方法是否可以合理地执行指定运算符类的目录项。例如,这可能包括提供所需的所有支持功能的测试。如果opclass无效,则amvalidate函数必须返回false。应该用ereport消息报告问题。
当然,索引的目的是支持对元组的扫描,以匹配可索引的条件,通常称为限定符或扫描关键字。索引扫描的语义在下面的第60.3节中更全面地描述。索引访问方法可以支持“普通”索引扫描、“位图”索引扫描,或者两者兼而有之。索引访问方法必须或可以提供的与扫描相关的功能是:
当然,索引的目的是支持对元组的扫描,以匹配可索引的条件,通常称为限定符或扫描关键字。索引访问方法可以支持“普通”索引扫描、“位图”索引扫描,或者两者兼而有之。索引访问方法必须或可以提供的与扫描相关的功能是:
准备索引扫描。nkeys and norderbys 参数指示将在扫描中使用的quals和排序运算符的数目;这些对于空间分配目的可能是有用的。注意,扫描键的实际值还没有提供。结果必须是一个palloc'd 结构。为了实现原因,索引访问方法必须通过调用RelationGetIndexScan()来创建此结构。在大多数情况下,ambeginscan除了调用该调用和获取锁之外几乎无能为力;索引扫描启动的有趣部分在amrescan中。
启动或重新启动索引扫描,可能有新的扫描键。(使用先前传递的密钥重新启动,NULL键和/或orderbys)。注意,操作员的密钥或订单数量不允许大于ambeginscan所传递的数字。在实践中,当通过嵌套循环连接选择新的外部元组时使用重启特征,因此需要新的密钥比较值,但是扫描密钥结构保持不变。
在给定的扫描中获取下一元组,在给定的方向上移动(索引中的前向或后向)。如果获得元组,则返回true,如果没有匹配元组,则返回false。在真实情况下,元组TID被存储到扫描结构中。注意“成功”仅仅意味着索引包含一个与扫描键相匹配的条目,而不是必须在堆中仍然存在元组,或者将通过调用方的快照测试。对于成功,AMGUTUPLE也必须设置scan->xs_recheck为真或假。FALSE意味着确定索引条目与扫描键匹配。TRUE意味着这是不确定的,并且扫描键所表示的条件必须在获取后对堆元组进行重新检查。此条款支持“有损”索引操作符。注意,复查只会扩展到扫描条件;部分索引谓词(如果有的话)永远不会被多个调用方重新检查。
如果索引仅支持索引扫描(即,amcanreturn返回true),那么在成功时,AM还必须检查 scan->xs_want_itup,如果这是真的,则必须返回索引项的原始索引数据。数据可以以scan->xs_itup 存储的索引元组指针的形式返回,使用元组描述符 scan->xs_itupdesc;或者以scan->xs_hitup 存储的一个堆指针的形式,用元组描述符scan->xs_hitupdesc。(后一种格式应该用于重建可能不适合索引的数据)。在这两种情况下,指针引用的数据的管理都是访问方法的责任。数据必须保持良好,至少直到下一个amgettuple, amrescan, or amendscan 调用扫描。
如果访问方法支持“普通”索引扫描,则只需要提供amgettuple函数。如果没有,则它的索引IndexAmRoutine中的amgettuple字段必须设置为NULL。
在给定的扫描中获取所有元组,并将它们添加到调用方提供TIDBitmap(即,或者将元组ID集插入到已经在位图中的任何集合)中。返回的元组数返回(这可能只是一个近似计数,例如一些AMs不检测重复)。在将元组ID插入位图中时,amgetbitmap可以指示对于特定元组ID需要重新检查扫描条件。这类似于amgettuple 的 xs_recheck 输出参数。注意:在当前的实现中,对该特征的支持与对位图本身的有损存储的支持相混淆,因此调用方重新检查扫描条件和重新索引元组的部分索引谓词(如果有的话)。然而,这并不总是正确的。在同一索引扫描中不能使用 amgetbitmap and amgettuple ;在使用amgetbitmap时也有其他限制。
如果访问方法支持“位图”索引扫描,则只需要提供amgetbitmap函数。如果没有,则其索引IndexAmRoutine中的amgetbitmap字段必须设置为NULL。
结束扫描和释放资源。扫描结构本身不应该被释放,但是必须由访问方法内部获取的任何锁或引脚。
标记当前扫描位置。访问方法只需要支持每个扫描的一个记忆扫描位置。
如果访问方法支持有序扫描,则只需要提供ammarkpos函数。如果没有,则它的索引矩阵结构中的ammarkpos字段可以设置为NULL。
将扫描恢复到最近标记的位置。
如果访问方法支持有序扫描,则只需要提供AMRePoPs函数。如果没有,则它的索引矩阵结构中的IndexAmRoutine字段可以设置为NULL。
除了支持普通索引扫描外,某些类型的索引可能希望支持并行索引扫描,这允许多个后端协作执行索引扫描。索引访问方法应该安排事物,使得每个协作过程返回由普通的非并行索引扫描执行的元组的子集,但是以这样的方式,这些子集的并集等于由普通的非P返回的元组集合。水平指数扫描此外,虽然不需要由并行扫描返回的元组的全局排序,但是在每个协作后端返回的元组子集的排序必须与所请求的顺序相匹配。可以实现以下功能来支持并行索引扫描:
估计并返回访问共享方法所需的动态共享内存字节数以执行并行扫描。(除此之外,这个数是代替并行索引扫描数据中AM独立数据所需的空间量)。
不需要为不支持并行扫描的访问方法或所需的附加字节数为零的访问方法实现此功能。
aminitparallelscan
这个函数将被调用来初始化并行扫描开始时的动态共享内存。目标将至少指向先前由amestimateparallelscan返回的字节数,并且该函数可以使用该空间量来存储它希望的任何数据。
不需要为不支持并行扫描的访问方法或在所需的共享内存空间不需要初始化的情况下实现此功能。
amparallelrescan
如果必须重新启动并行索引扫描,则调用该函数。它应该重置由aminitparallelscan设置的任何共享状态,使得扫描从一开始就重新开始。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值