在PostgreSQL中,删除表的操作是通过DropTable
函数来完成的。以下是该函数的核心逻辑:
void
DropTable(DropStmt *stmt)
{
DropTableInt(stmt, false);
}
static void
DropTableInt(DropStmt *stmt, bool concurrent)
{
...
// 检查是否存在依赖关系,如果有则抛出错误
checkDropRelStorage(relPersistence, nspname, stmt->arguments);
// 如果表存在,则删除表和相关的对象(例如索引、默认值等)
if (relPersistence == RELPERSISTENCE_TEMP)
RemoveTempTable(nspname, stmt->arguments);
else
RemoveRelations(stmt);
...
}
static void
RemoveRelations(DropStmt *stmt)
{
...
// 对于每个要删除的表,执行删除操作
foreach(cell, stmt->objects)
{
DropObjectDetails *details = (DropObjectDetails *)lfirst(cell);
RangeVar *rel = details->object;
// 查找并删除表
removeObject(rel, stmt->behavior, stmt->missing_ok, stmt->concurrent);
...
}
...
}
static void
removeObject(RangeVar *rel, DropBehavior behavior, bool missing_ok, bool concurrent)
{
...
// 获取并锁定表的描述信息
relId = RangeVarGetRelid(rel, AccessExclusiveLock, stmt->missing_ok);
...
// 删除表和相关的数据字典项
performDeletion(relId, behavior, rel->schemaname, concurrent);
...
}
static void
performDeletion(Oid objectId, DropBehavior behavior, const char *schemaName, bool concurrent)
{
...
// 执行删除表的SQL命令
object_access_hook_type = OBJECT_ACCESS_DELETE;
PG_TRY();
{
heap_drop_with_catalog(relRelation, objectId, behavior);
...
}
...
}
在上述代码中,DropTable
函数首先会检查是否存在依赖关系,如果存在则抛出错误。接着,它会检查要删除的表是否存在,如果存在则删除表以及与其相关联的所有对象(如索引、默认值等)。最后,它会发送一个SQL命令到后端执行实际的删除操作。