现在我serial
在PostgreSQL 13中用来生成表主键,但是今天发现ID跳了,ID空间有很大的差距。会浪费很多ID。我阅读了文档,发现 PostgreSQL 具有identity
作为 SQL 标准生成的主键。我找到了identity
在新版 PostgreSQL 中使用的建议,但我不知道 ID 是否连续。
我应该怎么做才能在 PostgreSQL 13 中获得没有间隙的主键 ID?
解决方案1:我尝试更改serial
为identity
这样:
BEGIN;
ALTER TABLE public.article ALTER id DROP DEFAULT; -- drop default
DROP SEQUENCE public.article_id_seq; -- drop owned sequence
ALTER TABLE public.article
-- ALTER clientid SET DATA TYPE int, -- not needed: already int
ALTER id ADD GENERATED ALWAYS AS IDENTITY (RESTART 2270886);
COMMIT;
仍有差距。
解决方案 2:我尝试添加关于我的应用程序插入文章的 redis 分发锁,如下所示:
def save_single(guid, pub_time, title, author, content, source, link):
if content is not None and len(content) > 0:
article = Article()
article_content = ArticleContent()
beta_parser = CnbetaParser()
second_parsed_content = beta_parser.parse_cnbeta_content(content, link)
article_content.article_content = second_parsed_content
cover_image = None
lock_identifier = None
try:
# cover_image = Utils.get_cover_image_url(self, content, link)
lock_identifier = acquire_lock("article-save", 5, 5)
article.save(title, guid, author, pub_time, article_content, link, source, cover_image)
except Exception as e:
logger.error("save article data error,rss:" + source.sub_url, e)
finally:
if lock_identifier is not None:
release_lock("article-save", lock_identifier)
else:
logger.error("article content is null,title:" + title)
仍有差距。
这个词是
IDENTITY
,不是IDENTIFY
。(我在你的问题中修复了它。)IDENTITY
列 ( ) 与旧列一样GENERATED { ALWAYS | BY DEFAULT } AS IDENTITY
基于 a 。你必须预料到序列号中的任何一个都有差距,这是它们的本质,没有什么可担心的。SEQUENCE
serial
我在 stackexchange 上的回答中解决了差异(您显然找到了将您转换为列的代码
serial
)IDENTITY
:但是我没有建议转换会消除 ID 空间中的空白。或者这将是可取的。如果您确实认为需要这样做,请考虑:
它以您在评论中已经收到的类似免责声明开始(以及一些替代方案):