Skip to content
项目
群组
代码片段
帮助
正在加载...
帮助
为 GitLab 提交贡献
登录/注册
切换导航
H
h2database
项目
项目
详情
活动
周期分析
仓库
仓库
文件
提交
分支
标签
贡献者
分枝图
比较
统计图
议题
0
议题
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
CI / CD
CI / CD
流水线
作业
计划
统计图
Wiki
Wiki
代码片段
代码片段
成员
成员
折叠边栏
关闭边栏
活动
分枝图
统计图
创建新议题
作业
提交
议题看板
打开侧边栏
Administrator
h2database
Commits
034abb3c
提交
034abb3c
authored
13 年前
作者:
Thomas Mueller
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
A persistent tree map (work in progress)
上级
af6af2f1
master
noel-pr1
plus33-master
pr/267
stumc-Issue#576
version-1.4.198
version-1.4.197
version-1.4.196
version-1.4.195
version-1.4.194
version-1.4.193
version-1.4.192
version-1.4.191
version-1.4.190
version-1.4.188
version-1.4.187
version-1.4.186
version-1.4.185
version-1.4.184
version-1.4.183
version-1.4.182
version-1.4.181
version-1.4.178
version-1.4.177
version-1.3
无相关合并请求
隐藏空白字符变更
内嵌
并排
正在显示
4 个修改的文件
包含
161 行增加
和
86 行删除
+161
-86
TestTreeMapStore.java
h2/src/test/org/h2/test/unit/TestTreeMapStore.java
+19
-8
BtreeMap.java
h2/src/tools/org/h2/dev/store/btree/BtreeMap.java
+12
-43
BtreeMapStore.java
h2/src/tools/org/h2/dev/store/btree/BtreeMapStore.java
+3
-2
Page.java
h2/src/tools/org/h2/dev/store/btree/Page.java
+127
-33
没有找到文件。
h2/src/test/org/h2/test/unit/TestTreeMapStore.java
浏览文件 @
034abb3c
...
...
@@ -48,24 +48,35 @@ public class TestTreeMapStore extends TestBase {
FileUtils
.
delete
(
fileName
);
BtreeMapStore
s
=
BtreeMapStore
.
open
(
fileName
);
BtreeMap
<
Integer
,
String
>
m
=
s
.
openMap
(
"data"
,
Integer
.
class
,
String
.
class
);
int
count
=
5
;
int
count
=
10000
;
// Profiler p = new Profiler();
// p.startCollecting();
// long t = System.currentTimeMillis();
for
(
int
i
=
0
;
i
<
count
;
i
++)
{
m
.
put
(
i
,
"hello "
+
i
);
assertEquals
(
"hello "
+
i
,
m
.
get
(
i
));
}
// System.out.println("put: " + (System.currentTimeMillis() - t));
// System.out.println(p.getTop(5));
// p = new Profiler();
//p.startCollecting();
// t = System.currentTimeMillis();
s
.
store
();
// System.out.println("store: " + (System.currentTimeMillis() - t));
// System.out.println(p.getTop(5));
m
.
remove
(
0
);
assertNull
(
m
.
get
(
0
));
for
(
int
i
=
1
;
i
<
count
;
i
++)
{
assertEquals
(
"hello "
+
i
,
m
.
get
(
i
));
}
s
.
close
();
//
s = BtreeMapStore.open(fileName);
//
m = s.openMap("data", Integer.class, String.class);
//
assertNull(m.get(0));
//
for (int i = 1; i < count; i++) {
//
assertEquals("hello " + i, m.get(i));
//
}
//
s.close();
s
=
BtreeMapStore
.
open
(
fileName
);
m
=
s
.
openMap
(
"data"
,
Integer
.
class
,
String
.
class
);
assertNull
(
m
.
get
(
0
));
for
(
int
i
=
1
;
i
<
count
;
i
++)
{
assertEquals
(
"hello "
+
i
,
m
.
get
(
i
));
}
s
.
close
();
}
private
void
testDefragment
()
{
...
...
This diff is collapsed.
Click to expand it.
h2/src/tools/org/h2/dev/store/btree/BtreeMap.java
浏览文件 @
034abb3c
...
...
@@ -331,57 +331,25 @@ public class BtreeMap<K, V> {
* A cursor to iterate over elements in ascending order.
*/
class
Cursor
implements
Iterator
<
K
>
{
Page
current
;
ArrayList
<
Page
>
parents
=
new
ArrayList
<
Page
>()
;
private
ArrayList
<
Page
.
CursorPos
>
parents
=
new
ArrayList
<
Page
.
CursorPos
>()
;
private
K
current
;
Cursor
(
Page
root
,
K
from
)
{
min
(
root
,
from
);
Page
.
min
(
root
,
parents
,
from
);
fetchNext
();
}
private
void
min
(
Page
p
,
K
key
)
{
int
todo
;
// while (n != null) {
// int compare = key == null ? -1 : n.compare(key);
// if (compare == 0) {
// current = n;
// return;
// } else if (compare > 0) {
// n = n.getRight();
// } else {
// parents.add(n);
// n = n.getLeft();
// }
// }
// if (parents.size() == 0) {
// current = null;
// return;
// }
// current = parents.remove(parents.size() - 1);
}
@SuppressWarnings
(
"unchecked"
)
public
K
next
()
{
int
todo
;
return
null
;
// Page c = current;
// if (c != null) {
// fetchNext();
// }
// return c == null ? null : (K) c.getKey();
K
c
=
current
;
if
(
c
!=
null
)
{
fetchNext
();
}
return
c
==
null
?
null
:
c
;
}
@SuppressWarnings
(
"unchecked"
)
private
void
fetchNext
()
{
int
todo
;
// Page r = current.getRight();
// if (r != null) {
// min(r, null);
// return;
// }
// if (parents.size() == 0) {
// current = null;
// return;
// }
// current = parents.remove(parents.size() - 1);
current
=
(
K
)
Page
.
nextKey
(
parents
);
}
public
boolean
hasNext
()
{
...
...
@@ -391,6 +359,7 @@ public class BtreeMap<K, V> {
public
void
remove
()
{
throw
new
UnsupportedOperationException
();
}
}
/**
...
...
This diff is collapsed.
Click to expand it.
h2/src/tools/org/h2/dev/store/btree/BtreeMapStore.java
浏览文件 @
034abb3c
...
...
@@ -21,6 +21,7 @@ import java.util.Properties;
import
java.util.TreeMap
;
import
org.h2.dev.store.FilePathCache
;
import
org.h2.store.fs.FilePath
;
import
org.h2.store.fs.FileUtils
;
import
org.h2.util.New
;
import
org.h2.util.SmallLRUCache
;
import
org.h2.util.StringUtils
;
...
...
@@ -140,7 +141,7 @@ public class BtreeMapStore {
private
void
open
()
{
meta
=
BtreeMap
.
open
(
this
,
"meta"
,
String
.
class
,
String
.
class
);
new
File
(
fileName
).
getParentFile
().
mkdirs
(
);
FileUtils
.
createDirectories
(
FileUtils
.
getParent
(
fileName
)
);
try
{
log
(
"file open"
);
file
=
FilePathCache
.
wrap
(
FilePath
.
get
(
fileName
).
open
(
"rw"
));
...
...
@@ -546,7 +547,7 @@ public class BtreeMapStore {
try
{
long
pos
=
getPosition
(
id
);
file
.
position
(
pos
);
ByteBuffer
buff
=
ByteBuffer
.
wrap
(
new
byte
[
1024
]);
ByteBuffer
buff
=
ByteBuffer
.
wrap
(
new
byte
[
8
*
1024
]);
// TODO read fully; read only required bytes
do
{
int
len
=
file
.
read
(
buff
);
...
...
This diff is collapsed.
Click to expand it.
h2/src/tools/org/h2/dev/store/btree/Page.java
浏览文件 @
034abb3c
...
...
@@ -7,13 +7,14 @@
package
org
.
h2
.
dev
.
store
.
btree
;
import
java.nio.ByteBuffer
;
import
java.util.ArrayList
;
/**
* A btree page implementation.
*/
class
Page
{
private
static
final
int
MAX_SIZE
=
4
;
private
static
final
int
MAX_SIZE
=
20
;
private
final
BtreeMap
<?,
?>
map
;
private
long
id
;
...
...
@@ -55,7 +56,7 @@ class Page {
*/
static
Page
read
(
BtreeMap
<?,
?>
map
,
long
id
,
ByteBuffer
buff
)
{
Page
p
=
new
Page
(
map
);
p
.
id
=
id
;
p
.
id
=
p
.
storedId
=
id
;
p
.
read
(
buff
);
return
p
;
}
...
...
@@ -79,7 +80,7 @@ class Page {
buff
.
append
(
" "
);
}
if
(
children
!=
null
)
{
buff
.
append
(
"["
+
children
[
i
]
+
"]"
);
buff
.
append
(
"["
+
children
[
i
]
+
"]
"
);
}
if
(
i
<
keys
.
length
)
{
buff
.
append
(
keys
[
i
]);
...
...
@@ -143,6 +144,70 @@ class Page {
return
-(
low
+
1
);
}
/**
* A position in a cursor
*/
static
class
CursorPos
{
Page
page
;
int
index
;
}
static
void
min
(
Page
p
,
ArrayList
<
CursorPos
>
parents
,
Object
key
)
{
int
todo
;
while
(
p
!=
null
)
{
int
x
=
key
==
null
?
0
:
p
.
findKey
(
key
);
if
(
p
.
children
!=
null
)
{
if
(
x
<
0
)
{
x
=
-
x
-
1
;
}
else
{
x
++;
}
p
=
p
.
map
.
readPage
(
p
.
children
[
x
]);
CursorPos
c
=
new
CursorPos
();
c
.
page
=
p
;
c
.
index
=
x
;
parents
.
add
(
c
);
}
else
{
if
(
x
<
0
)
{
x
=
-
x
-
1
;
}
CursorPos
c
=
new
CursorPos
();
c
.
page
=
p
;
c
.
index
=
x
;
parents
.
add
(
c
);
return
;
}
}
}
public
static
Object
nextKey
(
ArrayList
<
CursorPos
>
parents
)
{
int
todoTest
;
if
(
parents
.
size
()
==
0
)
{
return
null
;
}
while
(
true
)
{
// TODO avoid remove/add pairs is possible
CursorPos
p
=
parents
.
remove
(
parents
.
size
()
-
1
);
int
index
=
p
.
index
++;
if
(
index
<
p
.
page
.
keys
.
length
)
{
parents
.
add
(
p
);
return
p
.
page
.
keys
[
index
];
}
while
(
true
)
{
if
(
parents
.
size
()
==
0
)
{
return
null
;
}
p
=
parents
.
remove
(
parents
.
size
()
-
1
);
index
=
p
.
index
++;
if
(
index
<
p
.
page
.
children
.
length
)
{
parents
.
add
(
p
);
min
(
p
.
page
,
parents
,
null
);
break
;
}
}
}
}
private
int
size
()
{
return
keys
.
length
;
}
...
...
@@ -151,7 +216,7 @@ class Page {
return
children
==
null
;
}
private
Page
split
(
int
at
)
{
private
Page
split
Leaf
(
int
at
)
{
int
a
=
at
,
b
=
keys
.
length
-
a
;
Object
[]
aKeys
=
new
Object
[
a
];
Object
[]
bKeys
=
new
Object
[
b
];
...
...
@@ -160,22 +225,27 @@ class Page {
keys
=
aKeys
;
Object
[]
aValues
=
new
Object
[
a
];
Object
[]
bValues
=
new
Object
[
b
];
bValues
=
new
Object
[
b
];
System
.
arraycopy
(
values
,
0
,
aValues
,
0
,
a
);
System
.
arraycopy
(
values
,
a
,
bValues
,
0
,
b
);
values
=
aValues
;
long
[]
bChildren
;
if
(
children
==
null
)
{
bChildren
=
null
;
}
else
{
a
=
children
.
length
/
2
;
b
=
children
.
length
-
a
;
long
[]
aChildren
=
new
long
[
a
];
bChildren
=
new
long
[
b
];
System
.
arraycopy
(
children
,
0
,
aChildren
,
0
,
a
);
System
.
arraycopy
(
children
,
a
,
bChildren
,
0
,
b
);
children
=
aChildren
;
}
Page
newPage
=
create
(
map
,
bKeys
,
bValues
,
bChildren
);
Page
newPage
=
create
(
map
,
bKeys
,
bValues
,
null
);
return
newPage
;
}
private
Page
splitNode
(
int
at
)
{
int
a
=
at
,
b
=
keys
.
length
-
a
;
Object
[]
aKeys
=
new
Object
[
a
];
Object
[]
bKeys
=
new
Object
[
b
-
1
];
System
.
arraycopy
(
keys
,
0
,
aKeys
,
0
,
a
);
System
.
arraycopy
(
keys
,
a
+
1
,
bKeys
,
0
,
b
-
1
);
keys
=
aKeys
;
long
[]
aChildren
=
new
long
[
a
+
1
];
long
[]
bChildren
=
new
long
[
b
];
System
.
arraycopy
(
children
,
0
,
aChildren
,
0
,
a
+
1
);
System
.
arraycopy
(
children
,
a
+
1
,
bChildren
,
0
,
b
);
children
=
aChildren
;
Page
newPage
=
create
(
map
,
bKeys
,
null
,
bChildren
);
return
newPage
;
}
...
...
@@ -203,23 +273,40 @@ class Page {
if
(
parent
!=
null
)
{
parent
.
children
[
parentIndex
]
=
p
.
id
;
}
if
(!
p
.
isLeaf
())
{
if
(
p
.
size
()
>=
MAX_SIZE
)
{
// TODO almost duplicate code
int
pos
=
p
.
size
()
/
2
;
Object
k
=
p
.
keys
[
pos
];
Page
split
=
p
.
splitNode
(
pos
);
if
(
parent
==
null
)
{
Object
[]
keys
=
{
k
};
long
[]
children
=
{
p
.
getId
(),
split
.
getId
()
};
top
=
create
(
map
,
keys
,
null
,
children
);
p
=
top
;
}
else
{
parent
.
insert
(
parentIndex
,
k
,
null
,
split
.
getId
());
p
=
parent
;
}
}
}
int
index
=
p
.
findKey
(
key
);
if
(
p
.
isLeaf
())
{
if
(
index
>=
0
)
{
p
.
values
[
index
]
=
value
;
}
else
{
index
=
-
index
-
1
;
p
.
insert
(
index
,
key
,
value
,
0
)
;
if
(
p
.
size
()
>=
MAX_SIZE
)
{
int
pos
=
p
.
size
()
/
2
;
Object
k
=
p
.
keys
[
pos
]
;
Page
split
=
p
.
split
(
pos
)
;
if
(
parent
==
null
)
{
Object
[]
keys
=
{
k
};
long
[]
children
=
{
p
.
getId
(),
split
.
getId
()
};
Page
newRoot
=
create
(
map
,
keys
,
null
,
children
)
;
return
newRoot
;
}
break
;
}
index
=
-
index
-
1
;
p
.
insert
(
index
,
key
,
value
,
0
);
if
(
p
.
size
()
>=
MAX_SIZE
)
{
int
pos
=
p
.
size
()
/
2
;
Object
k
=
p
.
keys
[
pos
]
;
Page
split
=
p
.
splitLeaf
(
pos
);
if
(
parent
==
null
)
{
Object
[]
keys
=
{
k
};
long
[]
children
=
{
p
.
getId
(),
split
.
getId
()
}
;
top
=
create
(
map
,
keys
,
null
,
children
)
;
}
else
{
parent
.
insert
(
parentIndex
,
k
,
null
,
split
.
getId
());
}
}
...
...
@@ -236,7 +323,6 @@ class Page {
return
top
;
}
/**
* Remove a key-value pair.
*
...
...
@@ -317,8 +403,8 @@ class Page {
}
if
(
children
!=
null
)
{
long
[]
newChildren
=
new
long
[
children
.
length
+
1
];
copyWithGap
(
children
,
newChildren
,
children
.
length
,
index
);
newChildren
[
index
]
=
child
;
copyWithGap
(
children
,
newChildren
,
children
.
length
,
index
+
1
);
newChildren
[
index
+
1
]
=
child
;
children
=
newChildren
;
}
}
...
...
@@ -407,6 +493,10 @@ class Page {
*/
int
lengthIncludingTempChildren
()
{
int
len
=
length
();
if
(
len
>
1024
)
{
int
test
;
System
.
out
.
println
(
"??"
);
}
if
(
children
!=
null
)
{
int
size
=
children
.
length
;
for
(
int
i
=
0
;
i
<
size
;
i
++)
{
...
...
@@ -508,4 +598,8 @@ class Page {
}
}
public
Object
getKey
(
int
index
)
{
return
keys
[
index
];
}
}
This diff is collapsed.
Click to expand it.
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论