selectresultsetimpl.java

来自「RESIN 3.2 最新源码」· Java 代码 · 共 589 行

JAVA
589
字号
/* * Copyright (c) 1998-2008 Caucho Technology -- all rights reserved * * This file is part of Resin(R) Open Source * * Each copy or derived work must preserve the copyright notice and this * notice unmodified. * * Resin Open Source is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * Resin Open Source is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty * of NON-INFRINGEMENT.  See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License * along with Resin Open Source; if not, write to the *   Free SoftwareFoundation, Inc. *   59 Temple Place, Suite 330 *   Boston, MA 02111-1307  USA * * @author Scott Ferguson */package com.caucho.db.sql;import com.caucho.db.ResultSetImpl;import com.caucho.db.store.BlobInputStream;import com.caucho.db.store.Store;import com.caucho.db.table.Column;import com.caucho.db.table.TableIterator;import com.caucho.sql.SQLExceptionWrapper;import com.caucho.util.CharBuffer;import com.caucho.util.FreeList;import com.caucho.util.L10N;import com.caucho.util.QDate;import com.caucho.vfs.ReadStream;import com.caucho.vfs.TempBuffer;import com.caucho.vfs.TempStream;import com.caucho.vfs.WriteStream;import java.io.IOException;import java.sql.SQLException;public class SelectResultSetImpl extends ResultSetImpl {  private static final L10N L = new L10N(SelectResultSetImpl.class);    private static final FreeList<SelectResultSetImpl> _freeList =    new FreeList<SelectResultSetImpl>(16);    private final WriteStream _ws;  private final TempBuffer _buf;  private final ReadStream _rs;  private final byte []_buffer;  private final CharBuffer _cb;  private final TempStream _ts;  private static QDate _date = new QDate();    private Expr []_exprs;  private int []_types = new int[32];  private int []_offsets = new int[32];  private int []_lengths = new int[32];  private Store []_stores = new Store[32];  private TableIterator []_rows;  private int _lastColumn;  private SelectResultSetImpl()  {    _ws = new WriteStream();    _ws.setReuseBuffer(true);    _ts = new TempStream();    _rs = new ReadStream();    _rs.setReuseBuffer(true);    _buf = TempBuffer.allocate();    _buffer = _buf.getBuffer();    _cb = new CharBuffer();    _rows = new TableIterator[0];  }  public static SelectResultSetImpl create(Expr []exprs)  {    SelectResultSetImpl rs = _freeList.allocate();    if (rs == null)      rs = new SelectResultSetImpl();    rs.init(exprs);    return rs;  }  TableIterator []initRows(FromItem []fromItems)  {    if (_rows.length < fromItems.length)      _rows = new TableIterator[fromItems.length];          for (int i = 0; i < fromItems.length; i++) {      if (_rows[i] == null)	_rows[i] = new TableIterator();      _rows[i].init(fromItems[i].getTable());    }    return _rows;  }      private void init(Expr []exprs)  {    _exprs = exprs;        if (_offsets.length < _exprs.length) {      _offsets = new int[exprs.length];      _lengths = new int[exprs.length];      _types = new int[exprs.length];      _stores = new Store[exprs.length];    }    for (int i = 0; i < exprs.length; i++) {      _stores[i] = exprs[i].getTable();    }  }  void initRead()    throws IOException  {    _ts.openRead(_rs);  }  WriteStream getWriteStream()  {    _ts.openWrite();    _ws.init(_ts);        return _ws;  }    public boolean next()    throws SQLException  {    try {      ReadStream rs = _rs;      _lastColumn = 0;            int hasData = rs.read();      if (hasData <= 0)	return false;      int length = 0;      int fields = _exprs.length;      byte []buffer = _buffer;      for (int i = 0; i < fields; i++) {	int type = rs.read();	int sublen = 0;	switch (type) {	case Column.NONE:	  sublen = -1;	  break;	  	case Column.VARCHAR:	  int l0 = rs.read();	  int l1 = rs.read();	  int l2 = rs.read();	  int l3 = rs.read();		  sublen = ((l0 << 24) +		    (l1 << 16) +		    (l2 << 8) +		    (l3));	  break;	case Column.INT:	  sublen = 4;	  break;	case Column.LONG:	case Column.DOUBLE:	case Column.DATE:	  sublen = 8;	  break;	  	case Column.BLOB:	  sublen = 128;	  break;	  	default:	  throw new SQLException("Unknown column: " + type);	}	_types[i] = type;	_offsets[i] = length;	_lengths[i] = sublen;	if (sublen > 0) {	  rs.read(buffer, length, sublen);	  length += sublen;	}      }      return true;    } catch (IOException e) {      throw new SQLExceptionWrapper(e);    }  }  /**   * Returns the column index with the given name.   */  public int findColumnIndex(String name)    throws SQLException  {    for (int i = 0; i < _exprs.length; i++) {      if (_exprs[i].getName().equals(name))	return i + 1;    }    throw new SQLException(L.l("column `{0}' does not exist.", name));  }  /**   * Returns the string value of the given index.   */  public String getString(int index)    throws SQLException  {    _lastColumn = index;        byte []buffer = _buffer;    int offset = _offsets[index];    int length = _lengths[index];        switch (_types[index]) {    case Column.NONE:      return null;          case Column.INT:      {	int value = (((buffer[offset] & 0xff) << 24) +		     ((buffer[offset + 1] & 0xff) << 16) +		     ((buffer[offset + 2] & 0xff) << 8) +		     ((buffer[offset + 3] & 0xff)));	return String.valueOf(value);      }          case Column.LONG:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return String.valueOf(value);      }          case Column.DOUBLE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return String.valueOf(Double.longBitsToDouble(value));      }          case Column.DATE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return QDate.formatGMT(value);      }    case Column.VARCHAR:      return getStringValue(index);    case Column.BLOB:      return getBlobString(index);    default:      return null;    }  }  /**   * Returns the string value for the result set.   */  private String getStringValue(int index)    throws SQLException  {    _lastColumn = index;        int length = _lengths[index];    int offset = _offsets[index];        if (length < 0)      return null;    CharBuffer cb = _cb;    cb.clear();    byte []buffer = _buffer;    for (; length > 0; length--) {      cb.append((char) buffer[offset++]);    }    return cb.toString();  }  /**   * Returns the string value for the result set.   */  private String getBlobString(int index)    throws SQLException  {    _lastColumn = index;        int offset = _offsets[index];    CharBuffer cb = _cb;    cb.clear();    BlobInputStream is = null;    try {      is = new BlobInputStream(_stores[index], _buffer, offset);      int ch;      while ((ch = is.read()) >= 0) {	if (ch < 0x80)	  cb.append((char) ch);      }    } catch (IOException e) {      throw new SQLExceptionWrapper(e);    }    return cb.toString();  }  public int getInt(int index)    throws SQLException  {    _lastColumn = index;        byte []buffer = _buffer;    int offset = _offsets[index];    int length = _lengths[index];        switch (_types[index]) {    case Column.NONE:      return 0;          case Column.INT:      return (((buffer[offset + 0] & 0xff) << 24) +	      ((buffer[offset + 1] & 0xff) << 16) +	      ((buffer[offset + 2] & 0xff) << 8) +	      ((buffer[offset + 3] & 0xff)));          case Column.LONG:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return (int) value;      }          case Column.DOUBLE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return (int) Double.longBitsToDouble(value);      }    case Column.VARCHAR:      return Integer.parseInt(getString(index));    default:      return 0;    }  }  public long getLong(int index)    throws SQLException  {    _lastColumn = index;        byte []buffer = _buffer;    int offset = _offsets[index];    int length = _lengths[index];        switch (_types[index]) {    case Column.NONE:      return 0;          case Column.INT:      return (((buffer[offset] & 0xff) << 24) +	      ((buffer[offset + 1] & 0xff) << 16) +	      ((buffer[offset + 2] & 0xff) << 8) +	      ((buffer[offset + 3] & 0xff)));          case Column.LONG:    case Column.DATE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return value;      }          case Column.DOUBLE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return (long) Double.longBitsToDouble(value);      }    case Column.VARCHAR:      return Long.parseLong(getString(index));    default:      return 0;    }  }  /**   * Returns a double value from this column.   */  public double getDouble(int index)    throws SQLException  {    _lastColumn = index;        byte []buffer = _buffer;    int offset = _offsets[index];    int length = _lengths[index];        switch (_types[index]) {    case Column.NONE:      return 0;          case Column.INT:      return (((buffer[offset + 0] & 0xff) << 24) +	      ((buffer[offset + 1] & 0xff) << 16) +	      ((buffer[offset + 2] & 0xff) << 8) +	      ((buffer[offset + 3] & 0xff)));          case Column.LONG:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return value;      }          case Column.DOUBLE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return Double.longBitsToDouble(value);      }    case Column.VARCHAR:      return Double.parseDouble(getString(index));    default:      return 0;    }  }  public long getDate(int index)    throws SQLException  {    _lastColumn = index;        byte []buffer = _buffer;    int offset = _offsets[index];    int length = _lengths[index];        switch (_types[index]) {    case Column.NONE:      return 0;          case Column.LONG:    case Column.DATE:      {	long value = (((buffer[offset + 0] & 0xffL) << 56) +		      ((buffer[offset + 1] & 0xffL) << 48) +		      ((buffer[offset + 2] & 0xffL) << 40) +		      ((buffer[offset + 3] & 0xffL) << 32) +		      ((buffer[offset + 4] & 0xffL) << 24) +		      ((buffer[offset + 5] & 0xffL) << 16) +		      ((buffer[offset + 6] & 0xffL) << 8) +		      ((buffer[offset + 7] & 0xffL)));	return value;      }    case Column.VARCHAR:    case Column.BLOB:      {	String value = getString(index);		if (value == null)	  return 0;		synchronized (_date) {	  try {	    return _date.parseDate(value);	  } catch (Exception e) {	    throw new SQLExceptionWrapper(e);	  }	}      }    default:      throw new SQLException("unknown type:" + _types[index]);    }  }  /**   * Returns true if the last column read was null.   */  public boolean wasNull()  {    if (_lastColumn < 0)      return false;    else      return _lengths[_lastColumn] < 0;  }    public void close()  {    _freeList.free(this);  }}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?