Nano Hash - криптовалюты, майнинг, программирование

Поведение запроса SELECT с использованием executeUpdate

Я столкнулся со странным поведением при выполнении запроса SELECT с использованием Statement#executeUpdate() по ошибке. Хотя в Javadoc четко указано, что executeUpdate() throws SQLException, если данный оператор SQL создает объект ResultSet. Но когда я выполняю SELECT * from TABLE_NAME, я не получаю никаких исключений. Вместо этого я получаю возвращаемое значение, такое же, как и нет. выбранных строк, если нет. меньше или равно 10. Если нет. больше 10, возвращаемое значение всегда равно 10.

Connection conn;
Statement stmt;
try {
    conn = getConnection();
    stmt = conn.createStatement();
    int count = stmt.executeUpdate("SELECT * from TABLE_NAME");
    log.info("row count: " + count);
} catch (SQLException e) {
    log.error(e);
    // handle exception
} finally {
    DbUtils.closeQuietly(stmt);
    DbUtils.closeQuietly(conn);
}

Я использую Oracle 10g.

Я что-то упустил или драйверы сами определяют свое поведение?

19.12.2012

  • Имейте в виду, что javadoc определяет ожидаемое поведение, а не обязательно фактическое поведение, реализованное в конкретном драйвере! 19.12.2012

Ответы:


1

Такое поведение определенно противоречит Statement.executeUpdate API. Что интересно, java.sql.Driver.jdbcCompliant API говорит: «Драйвер может сообщать здесь true только в том случае, если он проходит тесты на соответствие JDBC». Я проверил oracle.jdbc.OracleDriver.jdbcCompliant - он возвращает true. Я также проверил com.mysql.jdbc.Driver.jdbcCompliant - он возвращает false. Но в той же ситуации, что вы описываете, выбрасывает

Exception in thread "main" java.sql.SQLException: Can not issue SELECT via executeUpdate().

Кажется, что драйверы JDBC непредсказуемы.

19.12.2012
  • То, что указано в спецификациях, и то, что поставляют поставщики, по-прежнему кажется двумя разными вещами. 19.12.2012
  • Комментарий к этому связанному вопросу объясняет странное поведение драйверов Oracle. stackoverflow.com/questions/4756094 / 28.01.2016

  • 2

    Согласно спецификации метод Statement.executeUpdate() возвращает the row count for SQL Data Manipulation Language (DML).

    UPD: я попытался сделать предположение о возвращаемом результате (который всегда равен ‹=10). Кажется, что реализация оператора оракула возвращает здесь число такого называемого premature batch count (согласно декомпилированным источникам класса OraclePreparedStatement). Это каким-то образом связано с операторами обновления. Возможно, это значение равно 10 по умолчанию.

    UPD-2: Согласно этому: Расширения эффективности: The premature batch flush count is summed to the return value of the next executeUpdate() or sendBatch() method.

    19.12.2012

    3

    Используемый вами запрос не создает ResultSet, но явно влияет на строки. Вот почему вы получаете не SQLException, а количество затронутых строк. Загадка в том, почему он не выходит за пределы 10. Может быть, это зависит от реализации драйвера Oracle JDBC.

    19.12.2012

    4

    Ваш sql-запрос должен получить все строки из table_name. Таким образом, вы можете использовать метод execute() вместо метода executeUpdate(). Поскольку более поздний метод обычно используется, когда ваша задача связана с языком управления базой данных, например запросом на обновление.

    19.12.2012
  • Не отвечает на вопрос. 19.12.2012

  • 5

    использовать

    int count = stmt.executeQuery("SELECT * from TABLE_NAME");

    вместо

    int count = stmt.executeUpdate("SELECT * from TABLE_NAME");

    для получения общего количества. строк.

    28.12.2012

    6

    Для общего случая (выберите или обновите):

        Statement st = conn.createStatement();
        st.execute(sql);
    
    13.08.2013
    Новые материалы

    Кластеризация: более глубокий взгляд
    Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..