Coding Planet
JDBC 프로그래밍: PreparedStatement, Sequence, Index 본문
1. JDBC Statement와 PreparedStatement
* JDBC의 DB접근 플로우
*JDBC 컴포넌트의 상호작용
(출처: [DataBase] JDBC란 ? (velog.io))
1. DriveManager
- 데이터 원본에 JDBC 드라이버를 통하여 커넥션을 만드는 역할을 한다. ClassforName()메소드를 통해 생성되며, 반드시 예외처리를 해야한다.
- 직접 객체 생성이 불가능하고, getConnection()메소드를 통해서 객체를 생성할 수 있다.
- 데이터베이스 벤더들이 JDBC API를 구현한 드라이버를 관리하고 DriveManager.getConnection()의 인자로 들어오는 특정값에 따라서 해당 특정 값에 해당되는 데이터벤더가 구현한 Conncection 타입의 객체를 반환한다.
2. Connection
- Connection 객체는 특정 데이터 원본과 연결된 커넥션을 나타낸다.
- Statement 객체를 생성할 때도 Connection 객체를 사용하여 createStatement()메소드를 호출하여 생성한다.
- SQL문장을 실행시키기 전에 우선 Connection객체가 있어야 한다.
3. Statement
- Connection 객체에 의해 프로그램에 리턴되는 객체에 의해 구현되는 일종의 메소드 집합을 정의한다.
- Connection 클래스의 createStatment()메소드를 호출하여 얻어지면, 생성된 Statement 객체로 질의문장을 String 객체에 담아 인자로 전달하며 excuteQuery()메소드 또는 excuteUpdate()메소드를 호출하여 SQL 질의를 수행한다.
- 쿼리문과 인자를 컴파일 수 실행, 쿼리문이 동적인 경우 적합하다.
- ex) String sql = "insert into member(id, pw) values (' " , +id+ " ',' " +pw+" ')"
4.PreparedStatement
- Connection 객체의 preparedStatement()메소드를 사용하여 객체를 생성한다.
- SQL문장이 미리 컴파일되고, 실행시간동안 인수 값을 위한 공간을 확보할 수 있다는 점에서 Statement와 다르다
- 각각의 인수에 대해 위치홀더(?)를 사용하여 SQL문장을 정의할 수 있게 해준다.
- 쿼리문을 컴파일 해 저장 후 호출 시 인자에 대입해 실행한다. 쿼리문이 정적인 경우 적합하다
- ex) String sql = " insert into member(id, pw) values (? , ?)";
2. PreparedStatement의 작동원리
1. 준비(Prepare)
- 애플리케이션은 SQL 문을 만들고 이를 DBMS로 전송한다
- 특정값을 지정하지 않고 ? 기호를 사용해서 set + 자료형()의 메소드 호출시에 전달받을 값의 자리르 지정한다.
- 작성형식은 (name, age)안의 컬럼의 갯수와 일치한다
- 예) INSERT INTO products(name, age) VALUES(?,?)
2. 컴파일(Compile)
- DMBS는 쿼리문을 컴파일(최적화 및 변환)하여 실행은 하지 않고 결과만 캐시(Cache)에 일단 저장한다(stmt와 차이)
- Cache는 자주 사용하는 데이터나 값을 미리 저장해두는 임시 저장소이다
- 예) PreparedStatement ps = conn.preparedStatement(sql);
- ps.setString(1, "홍길동"); -> set + 데이터자료형(물음표기호의순서번호(1부터 시장), 데이터);
- ps.setInt(2, 20);
3.실행(Execute)
- 쿼리문 실행
- 예) int res = ps.executeUpdate();
- executeUpdate()메소드를 호출해서 INSERT INTO products(name, age) VALUES('홍길동', 20) 실행
- UPDATE, DELETE 쿼리문도 실행가능
- SELECT SQL문을 실행하기 위해서는 executeQuery()메소드를 호출해야한다.
3. JDBC Statement와 PreparedStatement의 차이
- Statement를 사용하면 매번 쿼리를 수행할 때마다 4단계를 거치게 되지만 PreparedStatement는 처음 한번만 세 단계를 거친 후 캐시에 저장해 재사용 가능
- 만약 동일한 쿼리를 반복적으로 수행한다면 PreparedStatement가 DB에 적은 부하를 주며 성능이 빠르다.
- Statement는 executeQuery()나 excuteUpdate()를 실행하는 시점에 파라미터로 SQL문을 전달하는데, 이 때 전달된 SQL문은 완성된 형태로 한눈에 무슨 SQL인지 파악하기 쉽다.
- 하지만, Statement는 SQL문을 수행하는 과정에서 매번 컴파일을 하기 때문에 PreparedStatement에 비해 효율성이 떨어진다.
✨예제: PreparedStatement 사용해보기
PreparedStatement 인터페이스를 사용해서 emp_tbl 테이블에 새로운 데티어 저장하기 |
1. 실행할 SQL문을 작성하기
- INSERT INTO emp_tbl(empno, ename) VALES (?,?);
- *주의사항: 기본키, NOT NULL 제약 조건이 설정된 컬럼은 무조건 데이터 입력해야함. 즉, ename, empno 필수
- 데이터가 작을 때는 SELECT * FROM 으로 전체를 보지만 실무에서 데이터 규모가 커질 경우 전체 조회는 비효율적이므로 COUNT(*) WHERE을 사용하여 삽입하고자 하는 데이터가 중복인지 확인한다.
- 혹은 SELECT MAX(EMPNO)+1 FROM EMP_TBL // SELECT MIN(EMPNO)-1 FROM EMP_TBL;을 사용해서 중복되지 않는 사원번호를 만든다.
2. 이클립스에서 PreparedStatement로 INSERT 수행할 메소드 생성
3. SELECT MAX(empno)+1 FROM emp_tbl SQL문을 실행시키는 메소드 정의
4. main()메소드에서 실행하기
- SELECT MAX(empno)+1 FROM emp_tbl SQL문을 실행
-PreparedStatement로 INSERT 메소드 실행
5. ORACLE DB에서 확인해보기
6. INSERT 메소드 만들고 실행해보기
7. UPDATE() 메소드 만들고 실행해보기
4. ORACLE DBMS에서 만든 시퀀스 JDBC에서 사용하기
- 시퀀스 조회: SELECT * FROM USER_SEQUENCES
- 시퀀스 사용할 때 사용할 테이블 만들기: CREATE TABLE tuseq(seqno num)
- 시퀀스 사용: INSERT INTO 테이블이름() VALUES (MY_SEQ01_NEXTVAL);
- 시퀀스 제거: DROP SEQUENCE 시퀀스이름
- 시퀀스 수정: ALTER SEQUENCE sequence_name
- [INCREMENT BY n]
- [{MAXVALUE n | NOMAXVALUE}]
- [{MINVALUE n | NOMINVALUE}]
- [{CIRCLE | NOCIRCLE}]
- [{CACHE n | NOCACHE}]
- -> START WITH는 수정할 수 없다. 시작번호를 바꾸고 싶다면 시퀀스 삭제 후 다시 생성해야한다.
1. 시퀀스 만들기
2. JDBC에서 DDL(Data Definition Language) 실행하기: CREATE, DROP, ALTER
1) 위에서 만든 시퀀스 수정하기는 메소드만들기
** String sql 선언시 큰 따옴표와 시퀀스문 사이에 반드시 공백필요 " ALTER~"+" MAXVALUE~ "
2) SELECT문 실행하기
5. ORACLE DBMS에서 만든 INDEX JDBC에서 사용하기
- 생성: CREATE INDEX 인덱스명 ON 테이블명(컬럼명); ->인덱스명은 임의로 생성한다 IND_NAME, IDX_NAME
- 조회하기 :SELECT * FROM ALL_IND_COLUMNS WHERE TABLE_NAME = '인덱스명';
- 삭제하기: DROP INDEX 인덱스명;
- 인덱스명 수정하기: DROP INDEX 기존 인덱스명 TO 바뀔 인덱스명
- 컬럼수정은 불가. 인덱스 DROP 후 새로 CREATE해야함
1. 테스트용 테이블 만들기_EMPNO만 복사해오기
컬러차트
가나다라마 : #c7e2f9
가나다라마: #fae2d0
가나다라마: #faf8d0
가나다라마: #e7e8fc
가나다라마: #fcedf7
가나다라마: #F5A9F2
가나다라마: #F6CEF5
가나다라마: #FFFF00
가나다라마: #58FAF4
가나다라마: #9FF781
💭
'Server' 카테고리의 다른 글
[JSP] JSP(Java Server Page)란? Servlet와 JSP의 차이점, 지시어, 스크립팅 원소 (0) | 2023.03.20 |
---|---|
톰캣(Tomcat) 설치, 이클립스 연결 (0) | 2023.03.17 |
톰캣 설치 포트충돌, 오라클 포트 변경하기 (0) | 2023.03.17 |
[Servlet]Servlet, CGI, Servlet Container의미 (0) | 2023.03.17 |
[JDBC]ORACLE DBMS에서 만든 INDEX JDBC에서 사용하기 , Connection Pool (0) | 2023.01.26 |