简体   繁体   English

使用.Net从Oracle DB读取数据比使用Java快10倍

[英]Reading data from Oracle DB using .Net is 10 times faster than using Java

I'm reading 1 mln records from Oracle DB using .Net and Java. 我正在使用.Net和Java从Oracle DB中读取1百万条记录。 In .Net I'm using ODP.Net, in Java ojdbc6 thin client. 在.Net中,我在Java ojdbc6瘦客户端中使用ODP.Net。 In .Net reading data takes about 10 seconds, and in Java it takes nearly 2 minutes. 在.Net读取数据大约需要10秒钟,在Java中需要将近2分钟。 Why there is such huge difference ? 为什么会有这么大的差异?

Here is a code: 这是一个代码:

.Net: 。净:

      try
        {
            DateTime dt1 = DateTime.Now;

            OracleConnection con = new OracleConnection();
            con.ConnectionString = "Data Source=(DESCRIPTION=(ADDRESS_LIST=(ADDRESS=(PROTOCOL=TCP)(HOST=myHost)(PORT=myPort)))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME=myService)));User Id=myId;Password=myPass;";

            con.Open();
            string cmdQuery = "SELECT * FROM DROPME";

            OracleCommand cmd = new OracleCommand(cmdQuery);
            cmd.Connection = con;
            cmd.CommandType = CommandType.Text;

            int i = 0;
            OracleDataReader reader = cmd.ExecuteReader();
            while (reader.Read())
            {
                Object o1 = reader.GetValue(0);
                Object o2 = reader.GetValue(1);
                Object o3 = reader.GetValue(2);
                Object o4 = reader.GetValue(3);
                Object o5 = reader.GetValue(4);
                Object o6 = reader.GetValue(5);
                Object o7 = reader.GetValue(6);                    
                i++;
            }

            DateTime dt2 = DateTime.Now;

            double elapsed = (dt2 - dt1).TotalSeconds;
        }
        catch (Exception ex)
        {
            Console.WriteLine(ex.Message);
        }

Java: Java的:

    try
    {
        long t0 = System.currentTimeMillis();
        oracleDataSource = new OracleDataSource();
        oracleDataSource.setURL("jdbc:oracle:thin:myId/myPass@myHost:myPort:myService");
        Connection connection = oracleDataSource.getConnection();
        PreparedStatement statement = connection.prepareStatement("SELECT * FROM DROPME");
        ResultSet result = statement.executeQuery();
        int i = 0;
        while (result.next())
        {
            result.getObject(1);
            result.getObject(2);
            result.getObject(3);
            result.getObject(4);
            result.getObject(5);
            result.getObject(6);
            result.getObject(7);
            i++;
        }
        long t1 = System.currentTimeMillis();
        long elapsed = (t1 - t0)/1000;
        int t = 0;
    }
    catch (Exception ex)
    {
        ex.printStackTrace();
    }

EDIT: setFetchSize() did the job, thanks. 编辑:setFetchSize()完成了这项工作,谢谢。

In Java by default, ResultSets are completely retrieved and stored in memory. 默认情况下,在Java中,ResultSets被完全检索并存储在内存中。 This is not good for queries with large ResultSets. 这对于具有大型ResultSet的查询不利。 To use a streamed result u must use: 要使用流式结果,您必须使用:

stmt = conn.createStatement(java.sql.ResultSet.TYPE_FORWARD_ONLY, java.sql.ResultSet.CONCUR_READ_ONLY);
stmt.setFetchSize(Integer.MIN_VALUE);

I've not compared the time taken, but i guess this will be much faster. 我没有比较所花的时间,但我想这会快得多。

In my experience, the Oracle JDBC driver is poorly configured out-of-the-box for mass transfer. 根据我的经验,Oracle JDBC驱动程序配置不当,无法进行大规模传输。 By default, it only transfers 10 records across the network at a time. 默认情况下,它一次只能通过网络传输10条记录。 Therefore, if you have 1,000,000 records, the driver will incur 100,000 network accesses. 因此,如果您有1,000,000条记录,则驱动程序将进行100,000次网络访问。

You can tell the ResultSet how many records to fetch at a time with this code: 您可以使用此代码告诉ResultSet一次要获取的记录数:

result.setFetchSize(1000);

Feel free to experiment with different sizes. 随意尝试不同的尺寸。 It has dramatically decreased processing time (from minutes to seconds) in at least one application I have worked on. 它至少在我工作过的一个应用程序中大大减少了处理时间(从几分钟到几秒)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM