1/*
2 * Copyright (c) 2003, 2011, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26package com.sun.rowset.internal;
27
28import java.sql.*;
29import java.io.*;
30import java.lang.*;
31import java.util.*;
32
33/**
34 * A class that keeps track of a row's values. A <code>Row</code> object
35 * maintains an array of current column values and an array of original
36 * column values, and it provides methods for getting and setting the
37 * value of a column.  It also keeps track of which columns have
38 * changed and whether the change was a delete, insert, or update.
39 * <P>
40 * Note that column numbers for rowsets start at <code>1</code>,
41 * whereas the first element of an array or bitset is <code>0</code>.
42 * The argument for the method <code>getColumnUpdated</code> refers to
43 * the column number in the rowset (the first column is <code>1</code>);
44 * the argument for <code>setColumnUpdated</code> refers to the index
45 * into the rowset's internal bitset (the first bit is <code>0</code>).
46 */
47public class Row extends BaseRow implements Serializable, Cloneable {
48
49static final long serialVersionUID = 5047859032611314762L;
50
51/**
52 * An array containing the current column values for this <code>Row</code>
53 * object.
54 * @serial
55 */
56    private Object[] currentVals;
57
58/**
59 * A <code>BitSet</code> object containing a flag for each column in
60 * this <code>Row</code> object, with each flag indicating whether or
61 * not the value in the column has been changed.
62 * @serial
63 */
64    private BitSet colsChanged;
65
66/**
67 * A <code>boolean</code> indicating whether or not this <code>Row</code>
68 * object has been deleted.  <code>true</code> indicates that it has
69 * been deleted; <code>false</code> indicates that it has not.
70 * @serial
71 */
72    private boolean deleted;
73
74/**
75 * A <code>boolean</code> indicating whether or not this <code>Row</code>
76 * object has been updated.  <code>true</code> indicates that it has
77 * been updated; <code>false</code> indicates that it has not.
78 * @serial
79 */
80    private boolean updated;
81
82/**
83 * A <code>boolean</code> indicating whether or not this <code>Row</code>
84 * object has been inserted.  <code>true</code> indicates that it has
85 * been inserted; <code>false</code> indicates that it has not.
86 * @serial
87 */
88    private boolean inserted;
89
90/**
91 * The number of columns in this <code>Row</code> object.
92 * @serial
93 */
94    private int numCols;
95
96/**
97 * Creates a new <code>Row</code> object with the given number of columns.
98 * The newly-created row includes an array of original values,
99 * an array for storing its current values, and a <code>BitSet</code>
100 * object for keeping track of which column values have been changed.
101 */
102    public Row(int numCols) {
103        origVals = new Object[numCols];
104        currentVals = new Object[numCols];
105        colsChanged = new BitSet(numCols);
106        this.numCols = numCols;
107    }
108
109/**
110 * Creates a new <code>Row</code> object with the given number of columns
111 * and with its array of original values initialized to the given array.
112 * The new <code>Row</code> object also has an array for storing its
113 * current values and a <code>BitSet</code> object for keeping track
114 * of which column values have been changed.
115 */
116    public Row(int numCols, Object[] vals) {
117        origVals = new Object[numCols];
118        System.arraycopy(vals, 0, origVals, 0, numCols);
119        currentVals = new Object[numCols];
120        colsChanged = new BitSet(numCols);
121        this.numCols = numCols;
122    }
123
124/**
125 *
126 * This method is called internally by the <code>CachedRowSet.populate</code>
127 * methods.
128 *
129 * @param idx the number of the column in this <code>Row</code> object
130 *            that is to be set; the index of the first column is
131 *            <code>1</code>
132 * @param val the new value to be set
133 */
134    public void initColumnObject(int idx, Object val) {
135        origVals[idx - 1] = val;
136    }
137
138
139/**
140 *
141 * This method is called internally by the <code>CachedRowSet.updateXXX</code>
142 * methods.
143 *
144 * @param idx the number of the column in this <code>Row</code> object
145 *            that is to be set; the index of the first column is
146 *            <code>1</code>
147 * @param val the new value to be set
148 */
149    public void setColumnObject(int idx, Object val) {
150            currentVals[idx - 1] = val;
151            setColUpdated(idx - 1);
152    }
153
154/**
155 * Retrieves the column value stored in the designated column of this
156 * <code>Row</code> object.
157 *
158 * @param columnIndex the index of the column value to be retrieved;
159 *                    the index of the first column is <code>1</code>
160 * @return an <code>Object</code> in the Java programming language that
161 *         represents the value stored in the designated column
162 * @throws SQLException if there is a database access error
163 */
164    public Object getColumnObject(int columnIndex) throws SQLException {
165        if (getColUpdated(columnIndex - 1)) {
166            return(currentVals[columnIndex - 1]); // maps to array!!
167        } else {
168            return(origVals[columnIndex - 1]); // maps to array!!
169        }
170    }
171
172/**
173 * Indicates whether the designated column of this <code>Row</code> object
174 * has been changed.
175 * @param idx the index into the <code>BitSet</code> object maintained by
176 *            this <code>Row</code> object to keep track of which column
177 *            values have been modified; the index of the first bit is
178 *            <code>0</code>
179 * @return <code>true</code> if the designated column value has been changed;
180 *         <code>false</code> otherwise
181 *
182 */
183    public boolean getColUpdated(int idx) {
184        return colsChanged.get(idx);
185    }
186
187/**
188 * Sets this <code>Row</code> object's <code>deleted</code> field
189 * to <code>true</code>.
190 *
191 * @see #getDeleted
192 */
193    public void setDeleted() { // %%% was public
194        deleted = true;
195    }
196
197
198/**
199 * Retrieves the value of this <code>Row</code> object's <code>deleted</code> field,
200 * which will be <code>true</code> if one or more of its columns has been
201 * deleted.
202 * @return <code>true</code> if a column value has been deleted; <code>false</code>
203 *         otherwise
204 *
205 * @see #setDeleted
206 */
207    public boolean getDeleted() {
208        return(deleted);
209    }
210
211/**
212 * Sets the <code>deleted</code> field for this <code>Row</code> object to
213 * <code>false</code>.
214 */
215    public void clearDeleted() {
216        deleted = false;
217    }
218
219
220/**
221 * Sets the value of this <code>Row</code> object's <code>inserted</code> field
222 * to <code>true</code>.
223 *
224 * @see #getInserted
225 */
226    public void setInserted() {
227        inserted = true;
228    }
229
230
231/**
232 * Retrieves the value of this <code>Row</code> object's <code>inserted</code> field,
233 * which will be <code>true</code> if this row has been inserted.
234 * @return <code>true</code> if this row has been inserted; <code>false</code>
235 *         otherwise
236 *
237 * @see #setInserted
238 */
239    public boolean getInserted() {
240        return(inserted);
241    }
242
243
244/**
245 * Sets the <code>inserted</code> field for this <code>Row</code> object to
246 * <code>false</code>.
247 */
248    public void clearInserted() { // %%% was public
249        inserted = false;
250    }
251
252/**
253 * Retrieves the value of this <code>Row</code> object's
254 * <code>updated</code> field.
255 * @return <code>true</code> if this <code>Row</code> object has been
256 *         updated; <code>false</code> if it has not
257 *
258 * @see #setUpdated
259 */
260    public boolean getUpdated() {
261        return(updated);
262    }
263
264/**
265 * Sets the <code>updated</code> field for this <code>Row</code> object to
266 * <code>true</code> if one or more of its column values has been changed.
267 *
268 * @see #getUpdated
269 */
270    public void setUpdated() {
271        // only mark something as updated if one or
272        // more of the columns has been changed.
273        for (int i = 0; i < numCols; i++) {
274            if (getColUpdated(i) == true) {
275                updated = true;
276                return;
277            }
278        }
279    }
280
281/**
282 * Sets the bit at the given index into this <code>Row</code> object's internal
283 * <code>BitSet</code> object, indicating that the corresponding column value
284 * (column <code>idx</code> + 1) has been changed.
285 *
286 * @param idx the index into the <code>BitSet</code> object maintained by
287 *            this <code>Row</code> object; the first bit is at index
288 *            <code>0</code>
289 *
290 */
291    private void setColUpdated(int idx) {
292        colsChanged.set(idx);
293    }
294
295/**
296 * Sets the <code>updated</code> field for this <code>Row</code> object to
297 * <code>false</code>, sets all the column values in this <code>Row</code>
298 * object's internal array of current values to <code>null</code>, and clears
299 * all of the bits in the <code>BitSet</code> object maintained by this
300 * <code>Row</code> object.
301 */
302    public void clearUpdated() {
303        updated = false;
304        for (int i = 0; i < numCols; i++) {
305            currentVals[i] = null;
306            colsChanged.clear(i);
307        }
308    }
309
310   /**
311    * Sets the column values in this <code>Row</code> object's internal
312    * array of original values with the values in its internal array of
313    * current values, sets all the values in this <code>Row</code>
314    * object's internal array of current values to <code>null</code>,
315    * clears all the bits in this <code>Row</code> object's internal bitset,
316    * and sets its <code>updated</code> field to <code>false</code>.
317    * <P>
318    * This method is called internally by the <code>CachedRowSet</code>
319    * method <code>makeRowOriginal</code>.
320    */
321    public void moveCurrentToOrig() {
322        for (int i = 0; i < numCols; i++) {
323            if (getColUpdated(i) == true) {
324                origVals[i] = currentVals[i];
325                currentVals[i] = null;
326                colsChanged.clear(i);
327            }
328        }
329        updated = false;
330    }
331
332   /**
333    * Returns the row on which the cursor is positioned.
334    *
335    * @return the <code>Row</code> object on which the <code>CachedRowSet</code>
336    *           implementation objects's cursor is positioned
337    */
338    public BaseRow getCurrentRow() {
339        return null;
340    }
341}
342