Database
select 컬럼혹은표현식, 그룹함수(), 그룹함수()
from 테이블명
[where 조건식]
[group by 컬럼혹은표현식]
[order by 컬럼명]

select column, 그룹함수
from table
[where 조건식]
[group by 컬럼혹은표현식]
[having 그룹함수적용결과를 필터링하는 조건식]
[order by 컬럼]
-- 다중행 함수
-- employees 테이블에 등록된 모든 사원들의 수를 조회하기
select count(*)
from employees;
-- 60번 부서에 소속된 사원들의 수 조회하기
select count(*)
from employees
where department_id = 60;
-- 커미션을 받는 사원들의 수를 조회하기
select count(*)
from employees
where commission_pct is not null;
select count(commission_pct)
from employees;
-- 60번 부서에 소속된 사원들이 받는 급여의 총합, 최저급여, 최고급여, 평균급여를 조회하기
select sum(salary) 급여총합, min(salary) 최저급여, max(salary) 최고급여, avg(salary) 평균급여
from employees
where department_id = 60;
-- group by를 사용해서 테이블의 행들을 그룹화하기
-- 같은 부서에 소속된 사원들끼리 그룹화한 다음, 그룹함수를 적용해보기
SELECT department_id, COUNT(*)
FROM employees
GROUP BY department_id;
-- 부서별로 사원들을 그룹화한 다음, 부서별 급여총합, 급여평균을 조회하기
SELECT department_id, SUM(salary), ROUND(AVG(salary))
FROM employees
GROUP BY department_id;
-- 부서별로 사원들을 그룹화한 다음, 부서별 급여총합, 급여평균을 조회하기
-- 부서이름, 부서별 급여총합, 부서별 급여평균을 조회함
SELECT D.department_name, SUM(salary), ROUND(AVG(salary))
FROM employees E, departments D
WHERE E.department_id = D.department_id
GROUP BY D.department_name;
-- 부서별로 사원들을 그룹화하고, 같은 부서에 소속된 사원들을 직종으로 다시 그룹화 한 다음
-- 해당 그룹에 속하는 사원들의 숫자를 조회하기
SELECT department_id, job_id, COUNT(*)
FROM employees
GROUP BY department_id, job_id
ORDER BY 1, 2;
-- 급여별로 사원들을 그룹화 했을 때, 각 급여별 사원수를 조회하기
SELECT TRUNC(salary, -3) salary, COUNT(*)
FROM employees
GROUP BY TRUNC(salary, -3)
ORDER BY salary;
-- 급여별 사원수를 조회하기
SELECT (TRUNC(salary/5000) + 1) * 5000 || '미만' sal, COUNT(*)
FROM employees
GROUP BY TRUNC(salary/5000)
ORDER BY TRUNC(salary/5000);
-- 부서별 사원수를 조회했을 떄 사원수가 5미만인 부서의 아이디와 사원수를 조회하기
-- groupby가 있을때 having은 없어도되지만 having만 존재해서는 안된다.
SELECT department_id, COUNT(*)
FROM employees
GROUP BY department_id
HAVING COUNT(*) < 5;
-- 2007년에 입사한 사원들의 수를 직종아이디로 기준잡아 집계했을 때
-- 3명 이상 채용된 직종의 아이디와 사원수를 조회하기
SELECT job_id, COUNT(*)
FROM employees
WHERE hire_date >= to_date('2007/01/01') and hire_date < to_date('2008/01/01')
GROUP BY job_id
HAVING COUNT(*) >= 3
ORDER BY job_id;
-- 부서별 사원수를 집계했을 떄 사원수가 10명 이상인 부서의 아이디, 사원수를 조회하기
SELECT department_id, COUNT(*)
FROM employees
GROUP BY department_id
HAVING COUNT(*) >= 10;
-- with절을 사용해서 쿼리의 실행속도를 개선 및 쿼리의 가독성을 높이기
WITH employees_count
AS (
SELECT department_id dept_id, count(*) cnt
FROM employees
GROUP BY department_id
)
SELECT A.dept_id, B.department_name, A.cnt
FROM employees_count A, departments B
WHERE A.dept_id = B.department_id
AND A.cnt >= 5
ORDER BY A.dept_id;
package demo2.app;
import demo2.dao.UserDao;
import demo2.vo.User;
public class SimpleUserApp {
public static void main(String[] args) {
UserDao userDao = new UserDao();
// // 새로운 사용자정보 등록하기
// User user = new User();
// user.setId("hong");
// user.setPassword("zxcv1234");
// user.setName("홍길동");
// user.setEmail("hong@naver.com");
// user.setPhone("010-1234-5678");
//
//
// userDao.insertUser(user);
// System.out.println("새로운 사용자 정보가 등록되었습니다.");
// 사용자 정보 조회
User savedUser = userDao.getUserById("hong");
System.out.println("아이디 : " + savedUser.getId());
System.out.println("비밀번호 : " + savedUser.getPassword());
System.out.println("사용자명 : " + savedUser.getName());
System.out.println("전화번호 : " + savedUser.getPhone());
System.out.println("이메일 : " + savedUser.getEmail());
System.out.println("사용자 상태 : " + savedUser.getStatus());
System.out.println("사용자 정보 생성일 : " + savedUser.getCreatedDate());
// 사용자 정보 변경하기
// "hong" 아이디를 가진 사용자의 이메일, 전화번호 변경하기
User savedUser2 = userDao.getUserById("hong");
savedUser2.setEmail("gildong@gmail.com");
savedUser2.setPhone("010-5678-1234");
userDao.updateUser(savedUser2);
}
}
VARCHAR2(size)
CHAR(size)
LONG
CLOB
NUMBER(p, s)
DATE
TIMESTAMP
BLOB
ROWID
select rowid, department_id, department_name
from departments;
rowid departmet_id department_name
--------------------------------------------------------
AAAEAWAAEAAAACtAAA 10 Administration
AAAEAWAAEAAAACtAAB 20 Marketing
AAAEAWAAEAAAACtAAC 30 건희 영업팀
오브젝트번호 파일번호 블록번호 데이터번호
AAAEAW AAE AAAACt AAA
AAAEAb AAE AAAADN AAA
CREATE TABLE 테이블명 (
컬럼명 데이터타입(크기) [DEFAULT 기본값],
...
)
DROP TABLE 테이블명
ALTER TABLE 테이블명 ADD (컬럼명 데이터타입(크기) [DEFAULT 기본값]); ALTER TABLE 테이블명 MODIFY (컬럼명 테이터타입(크기) [DEFAULT 기본값]); ALTER TABLE 테이블명 DROP 컬럼명; RENAME 테이블명 TO 새테이블명 TRUNCATE TABLE 테이블명;
-- truncate는 테이블에서 모든 행을 제거한다.
-- 해당 테이블이 사용하는 저장공간을 해제한다.
-- truncate로 제거된 행은 rollback할 수 없다. CREATE SEQUENCE 시퀀스명;
-- 1부터 1씩 증가하는 번호가 발행된다.
CREATE SEQUENCE 시퀀스명
[INCREMENT BY a] a씩 증가한다.
[START WITH b] b부터 시작한다.
[{MAXVALUE c | NOMAXVALUE}] c가 최대값이다.
[{MINVALUE d | NOMINVALUE}] d가 최소값이다.
[{CYCLE | NOCYCLE}] 최대값/최소값이 도달했을 때 반복여부를 결정한다.
[{CACHE e | NOCACHE}] 일련번호를 e개 만큼 미리 할당해서 메모리에 캐시하거나, 캐시를 활용하지 않는다.
CREATE SEQUENCE 시퀀스명
INCREMENT BY 1
START WITH 1
NOMAXVALUE
NOMINVALUE
NOCYCLE
CACHE 20;
DROP SEQUENCE 시퀀스명
ALTER SEQUENCE 시퀀스명
[INCREMENT BY a]
[{MAXVALUE c | NOMAXVALUE}]
[{MINVALUE d | NOMINVALUE}]
[{CYCLE | NOCYCLE}]
[{CACHE e | NOCACHE}]
-- START WITH를 제외한 나머지 설정을 변경할 수 있다.
CREATE [OR REPLACE] VIEW 뷰이름
AS 서브쿼리
WITH READ ONLY
-- 서브쿼리는 가상의 테이블이 포함할 데이터를 조회하는 SELECT문
CREATE OR REPLACE VIEW 뷰이름
AS 서브쿼리
-- 뷰이름을 수정하려는 기존 뷰이름과 동일하게 지정하면 된다.
DROP VIEW 뷰이름
SELECT A.column, A.column, A.column
FROM (SELECT column, column, column, ...
FROM table1
WHERE 조건식) A
WHERE 조건식
CREATE INDEX 인덱스명
ON 테이블명 (컬럼명, ....)
DROP INDEX 인덱스명
CREATE INDEX 인덱스명
ON 테이블명 (오라클함수)
CREATE OR REPLACE TRIGGER 트리거명
{BEFORE | AFTER} -- 트리거 실행 싯점
{INSERT, UPDATE, DELETE} ON 테이블명 -- 이벤트종류
FOR EACH ROW -- 데이터 행의 변화가 생길 때 마다 실행된다
BEGIN
실행할 SQL
END;
트리거의 접두어(OLD, NEW)
| 작업 | OLD값 | NEW값 |
|---|---|---|
| INSERT | NULL | 추가된 값 |
| UPDATE | 갱신전의 값 | 갱신후의 값 |
| DELETE | 삭제전의 값 | NULL |
create table tb_order_history (
order_no number(7),
cust_no number(5),
order_status varchar2(20),
order_update_date date
); CREATE OR REPLACE TRIGGER order_history_trigger
AFTER
INSERT OR UPDATE ON tb_orders
FOR EACH ROW
BEGIN
insert into tb_order_history
(order_no, cust_no, order_status, order_update_date)
values
(:new.order_no, :new.cust_no, :new.order_status, sysdate);
END; ALTER TRIGGER 트리거명 ENABLE;
ALTER TRIGGER 트리거명 DISABLE;
DROP TRIGGER 트리거명;
-- 테이블에 저장된 각 행들의 ROWID 조회하기
SELECT ROWID, department_id, department_name
FROM departments;
select rowid, department_id, department_name
from departments;
-- 1부터 시작하는 시퀀스 생성하기
CREATE SEQUENCE product_seq
START WITH 1
NOCACHE;
SELECT product_seq.NEXTVAL FROM dual;
-- 상품테이블 생성하기
CREATE TABLE sample_products (
product_no number(8) primary key,
product_name varchar2(200) not null,
product_maker varchar2(100) not null,
product_category varchar2(100) not null,
product_price number(8) not null,
product_discount_price number(8) not null,
product_stock number(5) default 100,
product_sold_out char(1) default 'N',
product_created_date date default sysdate
);
-- 상품테이블에 상품정보 저장하기
INSERT INTO sample_products
(product_no, product_name, product_maker, product_category, product_price, product_discount_price)
values (product_seq.nextval, 'iphone12 plus', 'apple', '스마트폰', 1400000, 1200000);
-- 새로운 일련번호 조회하기
SELECT PRODUCT_SEQ.nextval FROM dual;
-- 현재 시퀀스의 일련번호 조회하기
SELECT product_seq.currval FROM dual;
------------- 퀴즈
-- 사원아이디, 이름, 소속부서 아이디, 소속부서명을 조회하기
SELECT e.employee_id, e.first_name, d.department_id, d.department_name
FROM employees E, departments D;
-- 60번부서에 소속된 사원들의 사원아이디, 이름, 급여, 직종아이디, 직종제목, 직종최저급여, 직종최고급여를 조회하기
SELECT e.employee_id, e.first_name, e.salary, j.job_id, j.job_title, j.min_salary, j.max_salary
FROM employees E, jobs J
WHERE e.department_id = 60
AND e.job_id = j.job_id;
-- 모든 사원들의 사원아이디, 이름, 급여, 급여등급을 조회하기
SELECT e.employee_id, e.first_name, e.salary, s.grade
FROM employees E, salary_grade S
WHERE e.salary >= s.min_salary and e.salary <= s.max_salary
ORDER BY e.employee_id;
-- 60번부서에 소속된 사원들의 사원아이디, 이름, 상사의 이름을 조회하기
SELECT e.employee_id, e.first_name, m.first_name
FROM employees E, employees M
WHERE e.employee_id = m.manager_id
AND e.department_id = 60;
-- 부서관리자가 있는 부서의 부서아이디, 부서명, 부서관리자 아이디, 부서관리자이름을 조회하기
SELECT d.department_id, d.department_name, d.manager_id, e.first_name
FROM departments D, employees E
WHERE d.department_id = e.department_id
AND d.manager_id = e.employee_id
AND d.manager_id is not null;
-- 부서관리자가 있는 부서의 부서소재지 도시명을 중복없이 조회하기
SELECT DISTINCT l.city
FROM departments D, locations L
WHERE d.manager_id is not null
AND d.location_id = l.location_id;
-- 소속부서명이 'Sales'이고, 급여등급이 'A'나 'B'에 해당하는 사원들의 아이디, 이름, 급여, 급여등급을 조회하기
SELECT e.employee_id, e.first_name, e.salary, s.grade
FROM employees E, departments D, salary_grade S
WHERE e.department_id = d.department_id
AND d.department_name = 'Sales'
AND e.salary >= s.min_salary and e.salary <= s.max_salary
AND s.grade in ('A', 'B');
-- 60번 부서에 소속된 사원들의 평균급여를 조회하기
SELECT AVG(salary)
FROM employees
WHERE department_id = 60;
-- 직종아이디별 사원수를 조회하기
SELECT job_id, COUNT(*)
FROM employees
GROUP BY job_id;
-- 급여 등급별 사원수를 조회하기
SELECT s.grade, COUNT(*)
FROM employees E, salary_grade S
WHERE e.salary >= s.min_salary AND e.salary < s.max_salary
GROUP BY s.grade;
-- 2007년 입사한 사원들의 월별 입사자 수를 조회하기
SELECT to_char(hire_date, 'MM') MM, COUNT(*)
FROM employees
WHERE hire_date >= to_date('2007/01/01') and hire_date < to_date('2008/01/01')
GROUP BY to_char(hire_date, 'MM')
ORDER BY to_char(hire_date, 'MM');