为什么当记录 > 大约 600 条时查询性能会急剧下降

Why query performance goes down sharply when records > about 600

为什么当我在 Oracle 中使用 "INSERT ALL" 大于约 600 条记录的查询时,查询性能会急剧下降? 你能教我吗?

我正在使用Spring + Mybatis + Oracle

以下是我的查询。

    INSERT ALL
    <foreach collection="list" item="record">
      INTO tablename (
        a,
        b,
        c,
        d,
        e,
        f,
        g,
        h,
        i,
        j,
        k,
        l,
        m,
        n,
        o
      ) VALUES (
        #{a},
        #{b},
        #{c},
        #{d},
        #{e},
        #{f},
        #{g},
        #{h},
        #{i},
        #{j},
        #{k},
        #{l},
        #{m},
        #{n},
        #{o}
      )
    </foreach>
    SELECT 1 FROM dual

(我更改了列和变量的名称。上面的查询正在运行)

请帮帮我~

原因很难说。通信块的大小、您的 oracle 进程的大小、您的连接类型、您正在使用的 Oracle 数据库的内存配置等等。

但另一个问题是,为什么您使用本质上是事务处理的批处理(bulk)相关工作。如果在 600 行处撞到这堵墙是个例外,那就忍受吧。如果您经常需要大量行(数千行),请研究批处理技术。

远离XML,也可能远离面向对象的技术。使用工具 as (s)ftp 将您的数据集传输到数据库服务器。使用外部表或 sqlloader 将数据导入数据库。 (不要通过网络连接使用 sqlloader,网络延迟会降低性能!!)。使用存储过程进行进一步处理。

正如@kordirko 提到的,它很慢很可能是因为您对 MyBatis insert 的使用没有进行批处理。

这是多行插入示例from MyBatis docs:

<insert id="insertAuthor" useGeneratedKeys="true"
    keyProperty="id">
  insert into Author (username, password, email, bio) values
  <foreach item="item" collection="list" separator=",">
    (#{item.username}, #{item.password}, #{item.email}, #{item.bio})
  </foreach>
</insert>

所以尝试这样使用它:

INSERT INTO tablename (
    a,
    b,
    c,
    d,
    e,
    f,
    g,
    h,
    i,
    j,
    k,
    l,
    m,
    n,
    o
  ) VALUES 
  <foreach collection="list" item="record">
  (
    #{a},
    #{b},
    #{c},
    #{d},
    #{e},
    #{f},
    #{g},
    #{h},
    #{i},
    #{j},
    #{k},
    #{l},
    #{m},
    #{n},
    #{o}
  )
</foreach>