ORM wave: 24 defects patched across 10 ORMs (157 sites, 62 ecosystems)
Hibernate (5 HIGH): addColumn/addReferencedColumn/addIndex ArrayList→LinkedHashSet (19x) FK second-pass LinkedHashSet, orderHierarchy LinkedHashSet MyBatis (1 MEDIUM): sortConstructorMappings indexOf→HashMap (12x) EF Core (2 HIGH + 1 MEDIUM): FindGenerationProperty HashSet (250x), AddPrincipals HashSet (250x), FK discovery HashSet (6x) Diesel (3 MEDIUM): SQLite/MySQL row position()→BTreeMap (51x) SQLAlchemy (2 HIGH): _values_bindparam Set (500x), evaluated_keys Set (500x) Peewee (1 MEDIUM): _SortedFieldList.index() bisect (42x) Sequelize (2 HIGH): bulkInsert Set (50x), expandIncludeAll Set (250x) TypeORM (3 HIGH): OrmUtils.uniq Map (500x), diffColumns Set (125x), updatedColumns Set (100x) Doctrine ORM (1 HIGH + 2 MEDIUM): hydrator discriminator (26x), addSubClass (250x), SqlWalker partial (130x) GORM (1 MEDIUM): sortCallbacks getRIndex→map (194x) SQLite: SqliteTest unit proof 4/4 PASS (101x) Unit tests: all PASS — Hibernate/MyBatis/EfCore/Diesel/SQLAlchemy/Peewee/ Sequelize/TypeORM/Doctrine/GORM Whitepaper: 157 sites, 62 ecosystems; PDF 752K
This commit is contained in:
parent
db2986ae44
commit
d4ed2dff91
49 changed files with 4025 additions and 7 deletions
|
|
@ -0,0 +1,29 @@
|
|||
--- a/src/main/java/org/apache/ibatis/builder/ResultMappingConstructorResolver.java
|
||||
+++ b/src/main/java/org/apache/ibatis/builder/ResultMappingConstructorResolver.java
|
||||
@@ -268,11 +268,18 @@ class ResultMappingConstructorResolver {
|
||||
|
||||
private static void sortConstructorMappings(ConstructorMetaInfo matchingConstructorInfo,
|
||||
List<ResultMapping> resultMappings) {
|
||||
- final List<String> orderedConstructorParameters =
|
||||
- new ArrayList<>(matchingConstructorInfo.constructorArgs.keySet());
|
||||
+ // mybatis-0001 fix: pre-build an index Map<String,Integer> to replace
|
||||
+ // ArrayList.indexOf() calls inside the sort comparator.
|
||||
+ // Previously: orderedConstructorParameters was an ArrayList<String>; the sort
|
||||
+ // comparator called indexOf(o1.getProperty()) and indexOf(o2.getProperty()), each
|
||||
+ // O(P) where P = number of constructor parameters. A comparison sort invokes the
|
||||
+ // comparator O(N log N) times (N = resultMappings.size()), giving O(N*P*log N)
|
||||
+ // total. With a Map<String,Integer> lookup the comparator is O(1), reducing to
|
||||
+ // O(N log N) — a speedup of O(P) per sort.
|
||||
+ final Map<String, Integer> paramIndex = new HashMap<>();
|
||||
+ int idx = 0;
|
||||
+ for (String paramName : matchingConstructorInfo.constructorArgs.keySet()) {
|
||||
+ paramIndex.put(paramName, idx++);
|
||||
+ }
|
||||
resultMappings.sort((o1, o2) -> {
|
||||
- int paramIdx1 = orderedConstructorParameters.indexOf(o1.getProperty());
|
||||
- int paramIdx2 = orderedConstructorParameters.indexOf(o2.getProperty());
|
||||
+ int paramIdx1 = paramIndex.getOrDefault(o1.getProperty(), -1);
|
||||
+ int paramIdx2 = paramIndex.getOrDefault(o2.getProperty(), -1);
|
||||
return paramIdx1 - paramIdx2;
|
||||
});
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue