日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Hibernate隐藏的宝石:pooled-lo优化器

發布時間:2023/12/3 编程问答 36 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Hibernate隐藏的宝石:pooled-lo优化器 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

介紹

在這篇文章中,我們將揭示一個序列標識符生成器,??它結合了標識符分配效率和與其他外部系統的互操作性(同時訪問底層數據庫系統)。

傳統上,有兩種序列標識符策略可供選擇。

  • 序列標識符,對于每個新值分配總是命中數據庫。 即使使用數據庫序列預分配,我們也要花費大量的數據庫往返費用。
  • seqhilo標識符,使用hi / lo算法。 該生成器在內存中計算一些標識符值,因此減少了數據庫往返調用。 這種優化技術的問題在于當前的數據庫序列值不再反映當前的最高內存生成值。 數據庫序列用作存儲區編號,這使得其他系統很難與所討論的數據庫表進行互操作。 其他應用程序必須了解高/低標識符策略的內部工作方式,才能正確生成非沖突標識符。

增強的標識符

Hibernate提供了一類新的標識符生成器 ,解決了原始標識符生成器的許多缺點。 增強的標識符生成器沒有固定的標識符分配策略。 優化策略是可配置的,我們甚至可以提供自己的優化實現。 默認情況下,Hibernate帶有以下內置優化器 :

  • none :每個標識符都是從數據庫中獲取的,因此等效于原始序列生成器。
  • hi / lo :它使用hi / lo算法,與原始seqhilo生成器等效。
  • 合并的 :此優化器使用高/低優化策略,但是當前內存中標識符的最高邊界是從實際數據庫序列值中提取的。
  • pooled-lo :它類似于優化器,但是數據庫序列值用作當前的內存最低邊界

在正式發布公告中 , 公告了合并的優化器可與其他外部系統進行互操作:

即使其他應用程序也在插入值,我們也將是絕對安全的,因為SEQUENCE本身將處理應用此增量大小。

這實際上是我們正在尋找的東西; 當其他外部系統在同一數據庫表中同時插入行時,標識符生成器既高效又不會沖突。

測試時間

以下測試將檢查新的優化器如何與其他外部數據庫表插入配合使用。 在我們的情況下,外部系統將是同一數據庫表/序列上的一些本機JDBC插入語句。

doInTransaction(new TransactionCallable<Void>() {@Overridepublic Void execute(Session session) {for (int i = 0; i < 8; i++) {session.persist(newEntityInstance());}session.flush();assertEquals(8, ((Number) session.createSQLQuery("SELECT COUNT(*) FROM sequenceIdentifier").uniqueResult()).intValue());insertNewRow(session);insertNewRow(session);insertNewRow(session);assertEquals(11, ((Number) session.createSQLQuery("SELECT COUNT(*) FROM sequenceIdentifier").uniqueResult()).intValue());List<Number> ids = session.createSQLQuery("SELECT id FROM sequenceIdentifier").list();for (Number id : ids) {LOGGER.debug("Found id: {}", id);}for (int i = 0; i < 3; i++) {session.persist(newEntityInstance());}session.flush();return null;} });

池優化器

我們將首先使用優化器策略:

@Entity(name = "sequenceIdentifier") public static class PooledSequenceIdentifier {@Id@GenericGenerator(name = "sequenceGenerator", strategy = "enhanced-sequence",parameters = {@org.hibernate.annotations.Parameter(name = "optimizer", value = "pooled"),@org.hibernate.annotations.Parameter(name = "initial_value", value = "1"),@org.hibernate.annotations.Parameter(name = "increment_size", value = "5")})@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "sequenceGenerator")private Long id; }

運行測試最終會引發以下異常:

DEBUG [main]: n.t.d.l.SLF4JQueryLoggingListener - Name: Time:0 Num:1 Query:{[insert into sequenceIdentifier (id) values (?)][9]} DEBUG [main]: n.t.d.l.SLF4JQueryLoggingListener - Name: Time:0 Num:1 Query:{[insert into sequenceIdentifier (id) values (?)][10]} DEBUG [main]: n.t.d.l.SLF4JQueryLoggingListener - Name: Time:0 Num:1 Query:{[insert into sequenceIdentifier (id) values (?)][26]} WARN [main]: o.h.e.j.s.SqlExceptionHelper - SQL Error: -104, SQLState: 23505 ERROR [main]: o.h.e.j.s.SqlExceptionHelper - integrity constraint violation: unique constraint or index violation; SYS_PK_10104 table: SEQUENCEIDENTIFIER ERROR [main]: c.v.h.m.l.i.PooledSequenceIdentifierTest - Pooled optimizer threw org.hibernate.exception.ConstraintViolationException: could not execute statementat org.hibernate.exception.internal.SQLExceptionTypeDelegate.convert(SQLExceptionTypeDelegate.java:72) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final] Caused by: java.sql.SQLIntegrityConstraintViolationException: integrity constraint violation: unique constraint or index violation; SYS_PK_10104 table: SEQUENCEIDENTIFIERat org.hsqldb.jdbc.JDBCUtil.sqlException(Unknown Source) ~[hsqldb-2.3.2.jar:2.3.2]

我不確定這是錯誤還是僅是設計限制,但是合并的優化器不滿足互操作性要求。

為了可視化發生的情況,我在下圖中總結了序列調用:

優化器檢索當前序列值時,它將使用它來計算最低的內存邊界。 最小值是實際的先前序列值,并且該值可能已被其他一些外部INSERT語句使用。

Pool-lo優化器

幸運的是,還有另外一個要測試的優化器(參考文檔中未提及)。 pool-lo優化器使用當前數據庫序列值作為最低的內存邊界,因此其他系統可以自由使用下一個序列值而不會冒標識符沖突的風險:

@Entity(name = "sequenceIdentifier") public static class PooledLoSequenceIdentifier {@Id@GenericGenerator(name = "sequenceGenerator", strategy = "enhanced-sequence",parameters = {@org.hibernate.annotations.Parameter(name = "optimizer",value = "pooled-lo"),@org.hibernate.annotations.Parameter(name = "initial_value", value = "1"),@org.hibernate.annotations.Parameter(name = "increment_size", value = "5")})@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "sequenceGenerator")private Long id; }

為了更好地了解此優化器的內部工作原理,下圖總結了標識符分配過程:

結論

一顆隱藏的寶石是大多數人甚至都不知道其存在的巨大特征之一。 pool-lo優化器非常有用,但是大多數人甚至都不知道它的存在。

  • 代碼可在GitHub上獲得 。

翻譯自: https://www.javacodegeeks.com/2014/07/hibernate-hidden-gem-the-pooled-lo-optimizer.html

總結

以上是生活随笔為你收集整理的Hibernate隐藏的宝石:pooled-lo优化器的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。