您可以将普通表与填充了值列表的内存表连接起来。
我不知道如何用 Java 做到这一点,但我知道如何用 C# 做到这一点。我认为Java应该可以实现类似的东西。
在这里阅读:http://forums.oracle.com/forums/thread.jspa?threadID=892457&tstart=375
让我们使用一组用户定义类型 (UDT)。
首先创建一个有 100 万行的表:
create table employees (id number(10) not null primary key, name varchar2(100) );
insert into employees
select level l, 'MyName'||to_char(level)
from dual connect by level <= 1e6;
1000000 rows created
commit;
exec dbms_stats.gather_schema_stats(USER, cascade=>TRUE);
不,我们转向 C# 代码:
让我们选择 id 为 3 和 4 的员工。
使用集合类型 MDSYS.SDO_ELEM_INFO_ARRAY 是因为如果我们使用这个已经预定义的 Oracle 类型,我们就不必定义我们自己的 Oracle 类型。您可以使用最多 1048576 个数字填充集合 MDSYS.SDO_ELEM_INFO_ARRAY。
using Oracle.DataAccess.Client;
using Oracle.DataAccess.Types;
[OracleCustomTypeMappingAttribute("MDSYS.SDO_ELEM_INFO_ARRAY")]
public class NumberArrayFactory : IOracleArrayTypeFactory
{
public Array CreateArray(int numElems)
{
return new Decimal[numElems];
}
public Array CreateStatusArray(int numElems)
{
return null;
}
}
private void Test()
{
OracleConnectionStringBuilder b = new OracleConnectionStringBuilder();
b.UserID = "sna";
b.Password = "sna";
b.DataSource = "ora11";
using (OracleConnection conn = new OracleConnection(b.ToString()))
{
conn.Open();
using (OracleCommand comm = conn.CreateCommand())
{
comm.CommandText =
@" select /*+ cardinality(tab 10) */ * " +
@" from employees, table(:1) tab " +
@" where employees.id = tab.column_value";
OracleParameter p = new OracleParameter();
p.OracleDbType = OracleDbType.Array;
p.Direction = ParameterDirection.Input;
p.UdtTypeName = "MDSYS.SDO_ELEM_INFO_ARRAY";
p.Value = new Decimal[] { 3, 4 };
comm.Parameters.Add(p);
int numPersons = 0;
using (OracleDataReader reader = comm.ExecuteReader())
{
while (reader.Read())
{
MessageBox.Show("Name " + reader[1].ToString());
numPersons++;
}
}
conn.Close();
}
}
}
employees.id 上的索引在省略提示 /*+ cardinality(tab 10) */ 时不使用。这个索引是Oracle创建的,因为id是主键列。
这意味着您不必填写临时表。值列表保留在 ram 中,您将表 employees 与内存 table(:1) 选项卡 中的值列表连接起来。
(wateenmooiedag=TTT)