KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > h2 > result > ResultDiskBuffer


1 /*
2  * Copyright 2004-2006 H2 Group. Licensed under the H2 License, Version 1.0 (http://h2database.com/html/license.html).
3  * Initial Developer: H2 Group
4  */

5 package org.h2.result;
6
7 import java.sql.SQLException JavaDoc;
8
9 import org.h2.engine.Constants;
10 import org.h2.engine.Database;
11 import org.h2.engine.Session;
12 import org.h2.store.DataPage;
13 import org.h2.store.FileStore;
14 import org.h2.util.ObjectArray;
15 import org.h2.value.Value;
16
17 class ResultDiskBuffer {
18
19     private static final int READ_AHEAD = 128;
20
21     private DataPage rowBuff;
22     private FileStore file;
23     private ObjectArray tapes;
24     private ResultDiskTape mainTape;
25     private SortOrder sort;
26     private int columnCount;
27
28     public ResultDiskBuffer(Session session, SortOrder sort, int columnCount) throws SQLException JavaDoc {
29         this.sort = sort;
30         this.columnCount = columnCount;
31         Database db = session.getDatabase();
32         rowBuff = DataPage.create(db, Constants.DEFAULT_DATA_PAGE_SIZE);
33         String JavaDoc fileName = session.getDatabase().createTempFile();
34         file = session.getDatabase().openFile(fileName, false);
35         file.autoDelete();
36         file.seek(FileStore.HEADER_LENGTH);
37         if (sort != null) {
38             tapes = new ObjectArray();
39         } else {
40             mainTape = new ResultDiskTape();
41             mainTape.pos = FileStore.HEADER_LENGTH;
42         }
43     }
44
45     public void addRows(ObjectArray rows) throws SQLException JavaDoc {
46         if (sort != null) {
47             sort.sort(rows);
48         }
49         DataPage buff = rowBuff;
50         long start = file.getFilePointer();
51         for (int i = 0; i < rows.size(); i++) {
52             buff.reset();
53             buff.writeInt(0);
54             Value[] row = (Value[]) rows.get(i);
55             for (int j = 0; j < columnCount; j++) {
56                 buff.writeValue(row[j]);
57             }
58             buff.fillAligned();
59             int len = buff.length();
60             buff.setInt(0, len);
61             buff.updateChecksum();
62             file.write(buff.getBytes(), 0, len);
63         }
64         if (sort != null) {
65             ResultDiskTape tape = new ResultDiskTape();
66             tape.start = start;
67             tape.end = file.getFilePointer();
68             tapes.add(tape);
69         } else {
70             mainTape.end = file.getFilePointer();
71         }
72     }
73
74     public void done() throws SQLException JavaDoc {
75         file.seek(FileStore.HEADER_LENGTH);
76     }
77
78     public void reset() {
79         if (sort != null) {
80             for (int i = 0; i < tapes.size(); i++) {
81                 ResultDiskTape tape = getTape(i);
82                 tape.pos = tape.start;
83                 tape.buffer = new ObjectArray();
84             }
85         } else {
86             mainTape.pos = FileStore.HEADER_LENGTH;
87         }
88     }
89
90     private void readRow(ResultDiskTape tape) throws SQLException JavaDoc {
91         int min = Constants.FILE_BLOCK_SIZE;
92         DataPage buff = rowBuff;
93         buff.reset();
94         file.readFully(buff.getBytes(), 0, min);
95         int len = buff.readInt();
96         buff.checkCapacity(len);
97         if(len-min > 0) {
98             file.readFully(buff.getBytes(), min, len - min);
99         }
100         buff.check(len);
101         tape.pos += len;
102         Value[] row = new Value[columnCount];
103         for (int k = 0; k < columnCount; k++) {
104             row[k] = buff.readValue();
105         }
106         tape.buffer.add(row);
107     }
108
109     public Value[] next() throws SQLException JavaDoc {
110         return sort != null ? nextSorted() : nextUnsorted();
111     }
112
113     private Value[] nextUnsorted() throws SQLException JavaDoc {
114         file.seek(mainTape.pos);
115         if (mainTape.buffer.size() == 0) {
116             for (int j = 0; mainTape.pos < mainTape.end && j < READ_AHEAD; j++) {
117                 readRow(mainTape);
118             }
119         }
120         Value[] row = (Value[]) mainTape.buffer.get(0);
121         mainTape.buffer.remove(0);
122         return row;
123     }
124
125     private Value[] nextSorted() throws SQLException JavaDoc {
126         int next = -1;
127         for (int i = 0; i < tapes.size(); i++) {
128             ResultDiskTape tape = getTape(i);
129             if (tape.buffer.size() == 0 && tape.pos < tape.end) {
130                 file.seek(tape.pos);
131                 for (int j = 0; tape.pos < tape.end && j < READ_AHEAD; j++) {
132                     readRow(tape);
133                 }
134             }
135             if (tape.buffer.size() > 0) {
136                 if (next == -1) {
137                     next = i;
138                 } else if (compareTapes(tape, getTape(next)) < 0) {
139                     next = i;
140                 }
141             }
142         }
143         ResultDiskTape t = getTape(next);
144         Value[] row = (Value[]) t.buffer.get(0);
145         t.buffer.remove(0);
146         return row;
147     }
148     
149     private ResultDiskTape getTape(int i) {
150         return (ResultDiskTape) tapes.get(i);
151     }
152
153     private int compareTapes(ResultDiskTape a, ResultDiskTape b) throws SQLException JavaDoc {
154         Value[] va = (Value[]) a.buffer.get(0);
155         Value[] vb = (Value[]) b.buffer.get(0);
156         return sort.compare(va, vb);
157     }
158
159     protected void finalize() {
160         if(!Constants.RUN_FINALIZERS) {
161             return;
162         }
163         close();
164     }
165
166     public void close() {
167         if (file != null) {
168             file.closeAndDeleteSilently();
169             file = null;
170         }
171     }
172
173 }
174
Popular Tags