powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Java [игнор отключен] [закрыт для гостей] / Использование PreparedStatement
10 сообщений из 10, страница 1 из 1
Использование PreparedStatement
    #38993008
alexander30
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Добрый день ,возник вопрос
Есть код

Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
    public class MarkDao extends Dao<Mark> {
     
    Connection connection=null;
    ResultSet resultSet=null;
    PreparedStatement insert=null;
        PreparedStatement select=null;
        PreparedStatement delete=null;
        PreparedStatement update=null;
     
    private String url="jdbc:mysql://localhost:3306/student";
    private String password="root";
    private String user="root";
    public Connection getConnection() {
     
    try {
    Class.forName("com.mysql.jdbc.Driver");
    if(connection==null){
    connection= DriverManager.getConnection(url, password, user);
    }
    } catch (ClassNotFoundException e) {
    e.printStackTrace();
    } catch (SQLException e) {
    e.printStackTrace();
    }
    return connection;
    }
     
     
     
    @Override
    public void insert(Mark obj) {
    String sql="insert into mark ( student_id, discipline_id, mark) values (?,?,?);";
    try {
    insert=connection.prepareStatement(sql);
    insert.setInt(1, obj.getStudent_id());
    insert.setInt(2, obj.getDiscipline_id());
    insert.setInt(3, obj.getMark());
    insert.executeUpdate();
    } catch (SQLException e) {
    e.printStackTrace();
        closePreparedStatement();
    }
    }
     
    @Override
    public List<Mark> select() {
    List<Mark> marks=new LinkedList<>();
    String sql="select id, student_id, discipline_id, mark from mark" ;
    Mark mark=null;
    try {
    select=connection.prepareStatement(sql);
    resultSet=select.executeQuery();
    while(resultSet.next()){
    mark=new Mark();
    mark.setId(resultSet.getInt("id"));
     
    mark.setStudent_id(resultSet.getInt("student_id"));
    mark.setDiscipline_id(resultSet.getInt("discipline_id"));
    mark.setMark(resultSet.getInt("mark"));
    marks.add(mark);
    }
    } catch (SQLException e) {
    e.printStackTrace();
    }finally {
    if(resultSet!=null){
    try {
    resultSet.close();
    } catch (SQLException e) {
    e.printStackTrace();
    }
    }
    }
        closePreparedStatement();
    System.out.println(marks);
    return marks;
      
    }
     
    @Override
    public void delete(Mark obj, int id) {
    String sql="delete from mark where id=?;";
    try {
    delete=connection.prepareStatement(sql);
    delete.setInt(1, id);
    delete.executeUpdate();
     
    } catch (SQLException e) {
    e.printStackTrace();
    }
        closePreparedStatement();
    }
     
    @Override
    public void update(Mark obj) {
    String sql="Update mark set mark=? where id=?;";
    try {
    update=connection.prepareStatement(sql);
     
    update.setInt(1, obj.getId());
    update.executeUpdate();
    } catch (SQLException e) {
    e.printStackTrace();
    }
    closePreparedStatement();
    }
     
    public void closeConnection() {
    try {
    if (connection != null) {
    connection.close();
    }
    } catch (Exception e) {
     
    }
     
    }
     
        public void closePreparedStatement() {
            try{
                if (insert!=null ){
                    insert.close();
                }
            }catch (SQLException e){
                e.printStackTrace();
            }
            try{
                if (select!=null ){
                    select.close();
                }
            }catch (SQLException e){
                e.printStackTrace();
            }
            try{
                if (update!=null ){
                    update.close();
                }
            }catch (SQLException e){
                e.printStackTrace();
            }
            try{
                if (delete!=null ){
                    delete.close();
                }
            }catch (SQLException e){
                e.printStackTrace();
            }
     
        }
    }





Мне говорят,что я не правильно использую PS , нужно "Один раз инициализировать , много раз его использовать и потом один раз каждый закрыть"

а у меня ,например здесь ,сколько раз будет вызываться insert - столько будет вызываться создание PS.
А должно быть один раз создать перед всеми вызовами, и одни раз закрыть после всех вызовов .

Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
    public void insert(Mark obj) {
    String sql="insert into mark ( student_id, discipline_id, mark) values (?,?,?);";
    try {
    insert=connection.prepareStatement(sql);
    insert.setInt(1, obj.getStudent_id());
    insert.setInt(2, obj.getDiscipline_id());
    insert.setInt(3, obj.getMark());
    insert.executeUpdate();
    } catch (SQLException e) {
    e.printStackTrace();
        closePreparedStatement();
    }
    }
     



Я не понимаю ,что мне нужно деалать(точнее как).
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993050
Фотография Blazkowicz
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
alexander30Мне говорят,что я не правильно использую PS , нужно "Один раз инициализировать , много раз его использовать и потом один раз каждый закрыть"

По-моему ваши советчики заблуждаются.

alexander30Я не понимаю ,что мне нужно деалать(точнее как).
Для начала перейти на try with resource
http://stackoverflow.com/questions/8066501/how-should-i-use-try-with-resources-with-jdbc
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993110
Leonid Kudryavtsev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Blazkowiczalexander30Мне говорят,что я не правильно использую PS , нужно "Один раз инициализировать , много раз его использовать и потом один раз каждый закрыть"

По-моему ваши советчики заблуждаются.

Почему они заблуждаются?
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993241
Фотография Blazkowicz
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Leonid KudryavtsevПочему они заблуждаются?
Потому что смысл фразы "один раз инициализировать" странный.
Переиспользовать PreparedStatement имеет смысл только для batch update. Я не вижу чтобы он здесь сильно нужен был. И топикастеру про batch\пакетную обработку тоже ничего не сказали.
План же самого запроса в RDBMS будет и так переиспользоваться, как раз из-за PreparedStatement и отсутствия динамических запросов. Основные проблемы приведенного кода в работе с Connection без DataSource, закрытием без finally и с полями, которые не только бесполезны но ещё и вылезут боком в многопоточном окружении.
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993273
Alexey Tomin
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
alexander30Есть код

Многабукв ;)

В коде каша.
В создание запроса каждый раз нет большой проблемы, если операции не идут часто. Т.е. это МОЖЕТ быть проблемой, но не факт, что будет. Но хранение PreparedStatement создаёт другие проблемы- протухания коннекта, к примеру. Или многопоточного вызова :D
А вот что надо сделать в первую очредь, так это:

1. Т.к. есть некое "extends Dao", то логично вынести создание коннекта в отдельный класс- вот он-то как раз пусть будет один на всех. Заодно, если случится, легко сделать пересоздание коннекта (реально связь с БД может теряться, если это не студенческий проект)
2. Если PreparedStatement создаётся каждый раз, то не надо полей в классе.
3. Надо использовать try-with-resource
4. Ещё плохо в Вашем поде явное указание пути к БД и логина/пароля. Это должно быть в ресурсах, или ХОТЯ БЫ константах.

alexander30Я не понимаю ,что мне нужно деалать(точнее как).

А это не вопрос. Это диагноз.
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993432
Сергей Арсеньев
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
BlazkowiczПлан же самого запроса в RDBMS будет и так переиспользоваться, как раз из-за PreparedStatement и отсутствия динамических запросов.
Не скажи. На днях показывал челу, что вынос создания PreparedStatement из цикла и его переиспользование убирает ошибку Oracle про количество открытых курсоров.
Так что на RDBMS надейся, а сам не плошай.
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993452
Фотография Blazkowicz
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Сергей Арсеньев Не скажи. На днях показывал челу, что вынос создания PreparedStatement из цикла и его переиспользование убирает ошибку Oracle про количество открытых курсоров.
Так что на RDBMS надейся, а сам не плошай.
Натянул сову на глобус. Я тут цикла не вижу.
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993780
Сергей Арсеньев
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Blazkowicz,

alexander30 а у меня ,например здесь ,сколько раз будет вызываться insert - столько будет вызываться создание PS.
А должно быть один раз создать перед всеми вызовами, и одни раз закрыть после всех вызовов .
То есть предполагается многократное количество вызовов insert подряд извне.
В теле класса его и не увидишь.

М.б. надо было создать, что-то типа static void insertAll(...)
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993786
Сергей Арсеньев
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
но в любом случае хранить в каждом DAO connection - это не совсем верно...
...
Рейтинг: 0 / 0
Использование PreparedStatement
    #38993962
Leonid Kudryavtsev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Народ, не путайте божий дар с яичницей.

PreparedStatement он по тому и PREPARED, что его можно создать один раз, один раз разпарсить SQL команду и дальше много раз делать INSERT.

С этой точки зрения, коллеги абсолютно правы. Будет экономиться как heap в java (меньше мусора), сетевой трафик (роунд-трипы), ресурсы сервера (не нужно будет делать лишних парсе) etc...

Дальше начинается яичница, то бишь Java. В которой разработчики решили не вводить ООП-диструкторы. Соответственно инициализируя PreparedStatement один раз и сохраняя его например в данных класса, есть риск получить resource leak.

IMHO & AFAIK
...
Рейтинг: 0 / 0
10 сообщений из 10, страница 1 из 1
Форумы / Java [игнор отключен] [закрыт для гостей] / Использование PreparedStatement
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]