복습

  1. 드라이버 로딩
    • 어떤 db서버를 연결하는지에 따라서 로등
  2. drivermanager -> 로딩된 드라이버를 통해서 db서버에 접속해서 connection객체 리턴해줌
  3. statement 객체 생성 : connection객체가 제공하는 createstatement에서 함

 

  • RuntimeException 
    • jvm이 예외처리해줌
    • 프로그램 실행을 중단시켜줌
    • 프로그램안에서 잘못된 구현에 의해서 발생되는게 대부분
  • NullPointerException
  • SQLException
    • 테이블 안 만들었는데 넣는거

 

  • executeQuery() - ResultSet
    • select 명령
  • excuteUpdate() - int값 리턴
    • insert - 1
    • delete - 삭제된 행의 갯수
    • update - 수정된 행의 갯수
    • ddl - 0

 

데이터 삽입

stmt.executeUpdate("insert into student values ('둘리', 100)");

 

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

public class SelectData1 {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				Statement stmt = conn.createStatement()){
			ResultSet rs = stmt.executeQuery("select * from student");
			while(rs.next()) {
				System.out.println(rs.getString("name")+"학생은 "+rs.getInt("score")+"점 입니다.");
			}				
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		}
	}
}
  • try 리소스 구문으로 예외처리
  • try (Connection conn = DriverManager.getConnection(url, user, passwd);
    Statement stmt = conn.createStatement())
    • try블록이 끝날 때, 자동으로 close가 된다. 
    • 아무변수나 선언 X
      • closerable 상속받는 객체만 만들기 가능 
      • 닫아줘야하는 객체만
    • 변수 선언과 객체 생성 동시에 
    • 얼마든지 올 수 있음 (몇개든)

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.util.Scanner;

public class InsertData2 {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				PreparedStatement pstmt = conn.prepareStatement("insert into student values (?, ?)");
				Scanner scan = new Scanner(System.in);){
			while(true) {
				System.out.print("학생 이름을 입력하세요 : ");
				String name = scan.nextLine();
				System.out.print("학생 점수를 입력하세요 : ");
				int score = Integer.parseInt(scan.nextLine());
				pstmt.setString(1,  name);
				pstmt.setInt(2, score);
				pstmt.executeUpdate();
				System.out.println("student 테이블에 데이터 삽입 완료");
				System.out.print("계속 입력하겠습니까?(y/n)");
				String aws = scan.nextLine();
				if (aws.equalsIgnoreCase("y")) {
					continue;
				} 
				System.out.println("student 테이블 데이터 삽입 작업 종료");
				break;
			}
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		} 
	}
}
  • statement
    • 그때, 그때 sql명령을 메소드에 담아서 호출
    • 바이너리 데이터 처리 못 함
    • stmt.executeUpdate("insert into student values ('둘리', 100)");
      • 직접 지정할 때, 문자면 단일인용부호 사용해야한다. 
    • stmt.executeUpdate("insert into student values ("+name+","+scroe+")");
      • scanner로 객체 받을 때, 적는게 어렵
  •  PreparedStatement
    • sql 명령 수행
    • 객체 생성할 때, 미리 sql 명령 준비시켜놓음
      • 미리 생성된 sql 명령만 실행 가능
      • sql 명령의 해석이 되어져있음
    • 똑같은 sql문을 여러번 수행할 때, 데이터 값만 달라졌을 때 적합함
    •  (?, ?) - 동적 파라미터
      • 미지의 데이터 값
      • 나중에 정할 때 좋음
      • pstmt.setString(1,  name);
    • 바이너리 값 넣을 수 있다. 
      • 이미지,, 
    • pstmt.executeUpdate();
      • 아구먼트 쓰면 안 됨
      • 반드시 수행해줘야 sql에 업데이트 된다. 

 

파일

  • 절대 패스
    • C:/Temp/test.png
    • C:\\Temp\\test.png
  • 상대 패스 
    • 현재 디렉토리가 어디있냐에 따라 달름
    • 프로젝트 폴더가 현재 디렉토리가 된다. 
    • ../../Temp/test.png
package mysql.level1;
import java.io.*;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.util.Scanner;

public class InsertImage {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				Scanner scan = new Scanner(System.in);
				PreparedStatement pstmt = conn.prepareStatement("INSERT INTO imgtest (filename, filecontent) VALUES (?, ?)")){
			System.out.print("저장할 이미지 파일명을 절대 패스로 입력하세요 : ");
			String name = scan.nextLine();
			File imgFile = new File(name);
			if (imgFile.exists()) {
				int pointIndex = imgFile.getName().indexOf('.');
				String imgName = imgFile.getName().substring(0, pointIndex);
				System.out.println(imgFile.getName().substring(0, pointIndex));
				FileInputStream fin = new FileInputStream(imgFile); 
				pstmt.setString(1, imgName); 
				pstmt.setBinaryStream(2, fin, (int)imgFile.length());
				pstmt.executeUpdate(); 
				System.out.println("이미지 삽입 성공");
			} else {
				System.out.println("[오류] 이미지가 존재하지 않음");
			}
		} catch(Exception e) {
			System.out.println(e);
		}
	}
}
  • INSERT INTO imgtest (filename, filecontent) VALUES (?, ?)
    • 순서대로 넣는거면 컬럼명 생략 가능
  • File imgFile = new File(name);
    • 패스 정보 줌
  • imgFile.getName().indexOf('.');
    • 파일이름만 뽑아 내는 것
      • 점 이후 다 날리는 것
    • ex) c:/Temp/hi.png
  • pstmt.setBinaryStream(2, fin, (int)imgFile.length());
    • 읽어서 db테이블에 넣어줌
    • 실행되기 전에 이미지 파일 읽어서 넣어줌
    • 첫번째 매개변수 : 매개변수 번호
    • 두번째 매개변수 : inputStream 개체
    • 세번째 매개변수 : 바이트 수

 

파일 저장되어 있는거 읽고 쓰기

package mysql.level1;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.Scanner;

public class SelectImage {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		}
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				Scanner scan = new Scanner(System.in);
				PreparedStatement pstmt = conn.prepareStatement("SELECT filename, filecontent FROM imgtest WHERE filename = ?");) {
			System.out.print("읽으려는 이미지의 파일명(확장자제외)을 입력하세요 : ");
			String name = scan.nextLine();
			pstmt.setString(1, name);
			ResultSet rs = pstmt.executeQuery();
			if (rs.next()) {
				File imgFile = new File("c:/Temp/"+rs.getString("filename")+"_new.png");
				InputStream is = rs.getBinaryStream("filecontent");
				FileOutputStream fos = new FileOutputStream(imgFile);
				byte[] b = new byte[2048];
				int n;
				while ((n = is.read(b)) > 0) {
					fos.write(b, 0, n);
				}
				fos.close();
				rs.close();
			} else {
				System.out.print(name + "이라는 파일명으로 저장된 이미지가 존재하지 않습니다. ");
			}
			System.out.println("이미지 읽기 성공");
		} catch (Exception e) {
			System.out.println(e);
		}
	}
}
  • rs.getBinaryStream("filecontent");
    • inpustream객체 리턴
    • 읽을 수 있는 객체 
  • stream 
    • 데이터 통로 역활
    • inputStream 통로 만들고
    • outputStream 통로 만들고
  • (n = is.read(b)) > 0
    • db테이블에서 2048byte 읽음
  • 출력할 때 파일이 없으면 새로 만듦

 

SelectData2.java

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Scanner;

public class SelectData2 {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				PreparedStatement pstmt = conn.prepareStatement("select score from student where name = ?");
				Scanner scan = new Scanner(System.in);){
		    System.out.print("학생 이름을 입력하세요 : ");
		    String name = scan.nextLine();
		    pstmt.setString(1, name);
			ResultSet rs = pstmt.executeQuery();
			if(rs.next()) 
				System.out.println(name + "학생의 점수 : " + rs.getInt("score"));
			 else 			
				 System.out.println(name + "학생에 대한 데이터가 없습니다.");
			 System.out.println("수행 종료...");
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		}
	}
}
  • next가 한번이라도 해야 테이블에 데이터가 있는지 안다. 
  • 데이터가 없으면 resultset객체는 반환되는데 (비어있는 resultset)
    • 첫번째 값이 false
    • 값이 없는 건 next() 객체를 한번이라도 수행해야 알 수 있다.

 

SelectData3.java

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Scanner;

public class SelectData3 {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				PreparedStatement pstmt = conn.prepareStatement("select name, score from student where score>=  ? order by score desc");
				Scanner scan = new Scanner(System.in);){
		    System.out.print("점수를 입력하세요 : ");
		   int score = Integer.parseInt(scan.nextLine());
		    pstmt.setInt(1, score);
			ResultSet rs = pstmt.executeQuery();
			if(rs.next()) {
				System.out.println("[ 점수가 " + score + " 이상인 학생 이름(점수가 높은 순) ]");
				do {
					System.out.println(rs.getString("name") + " : " + rs.getInt("score"));
				} while(rs.next());
			} else 			
				 System.out.println("점수가 " + score + " 이상인 학생은 존재하지 않습니다.");
			 System.out.println("수행 종료...");
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		}
	}
}
  • do while문 사용

 

UpdateDate.java

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.util.Scanner;
import java.sql.PreparedStatement;

public class UpdateData {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				PreparedStatement pstmt = conn.prepareStatement("update student set score = ? where name = ?");
				Scanner scan = new Scanner(System.in);){
			System.out.print("학생 이름을 입력하세요 : ");
		    String name = scan.nextLine();
			System.out.print("학생 점수를 입력하세요 : ");
			int score = Integer.parseInt(scan.nextLine());
			pstmt.setInt(1,  score);
		    pstmt.setString(2, name);
			int updateNum = pstmt.executeUpdate();
			System.out.println("student 테이블에서 " +updateNum + "행 변경 완료");						
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		} 
	}
}

 

package mysql.level1;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.util.Scanner;
import java.sql.PreparedStatement;

public class DeleteData2 {
	public static void main(String[] args) {
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
			return;
		} 
		String url = "jdbc:mysql://localhost:3306/jdbcdb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		try (Connection conn = DriverManager.getConnection(url, user, passwd);
				PreparedStatement pstmt = conn.prepareStatement("delete from student where score between ? and ?");
				Scanner scan = new Scanner(System.in);){
			System.out.print("삭제하려는 최저 점수 입력 : ");
			int minScore = Integer.parseInt(scan.nextLine());
			System.out.print("삭제하려는 최고 점수 입력 : ");
			int maxScore = Integer.parseInt(scan.nextLine());
			pstmt.setInt(1, minScore);
			pstmt.setInt(2, maxScore);
			int delNum = pstmt.executeUpdate();
			System.out.println("student 테이블에서 " + delNum + "행 삭제 완료");									
		} catch (SQLException se) {
			System.out.println(se.getMessage());
		} 
	}
}

[java.io 패키지]

  • File 
    • 자바 프로그램안에서 파일에 대한 처리를 하겠다. 
    • 자바 - 객체로 다 봐서 file사용함 
    • 운영체제에 무관해서 io 설계한 것
  • 입출력 - 실제 주고받는 객체는 동일함 (스트림 객체)
    •  파일
      • 파일을 열어서 내보내겠다.
    • 네트워크
      • 소켓입출력을 통해서
      • 최종 목적지 : 소켓
    • 표준 입출력
      • system.out.println()
      • scanner - System.in (키보드로부터 읽는다)
        • system이라는 클래스에 system.in, system.out, system.err이라는 static형 멤버 변수를 정의해놨음
          • 표준 입력을 관장하는 친구 - system.in
          • system.out, system.err -> 모니터 화면으로 나옴
  • 스트림 객체
    • 입력용이냐 출력용이냐
    • 바이트단위의 입출력? 문자 단위의 입출력?
  • 클래스 이름에
    • inpuststrem, ---OuputStream : 바이트 스트림
      • 이미지같은 파일을 io할 때, 
    • ---Reader, Writer 
      • 파일 읽고, 쓰는 것

'study > JAVA 전문가' 카테고리의 다른 글

[sql] roll back 연습문제  (0) 2021.12.21
[JDBC] 방명록  (0) 2021.12.21
JDBC  (0) 2021.12.20
mysql 5  (0) 2021.12.20
mysql 4 - 연습문제  (0) 2021.12.20
  • jdbc api
    • 실제 수행코드는 정의되어 있지 않다. 
    • 매소드 호출 방식만 정의해 놨다. 
    • DB 서버마다 처리하는 방식이 다르다. 
      • 인터페이스로
      • 인터페이스의 자식 클래스를 jdbc driver로 대신하는 것
      • 알맹이는 드라이버가 제공 
    • 공통적인건 class
    • 코드는 같은데 driver만 다른거 준비하면 된다. 
    • 객체 생성을 대신해주는 매소드 (팩토리 매소드)
    • 인터페이스 활용이 많이 돋보이는 기술

 

  • executeQuery()
    • resultset으로 반환함
      • next() 행 단위로 옮겨서 여러 값 추출

 

주요 JDBC API

  • statement -> (확장) preparedStatement
  • DriverManger 
    • DB서버에 대한 접속이 선행되어야 한다. drivermanager.getconnection

 

  1. jdbc 로딩
    Class.forName("com.mysql.cj.jdbc.Driver");
  2. jdbc url ( Uniform Resource Locator ) -> 위치 알릴 때 단일화
    "jdbc:mysql://localhost:3306/sqldb?characterEncoding=UTF-8&serverTimezone=UTC";​
    • 어떤 DB 서버를 어떤 driver에 연결할지 
    • jdbc:어떤 서버://[호스트 네임][:port]/dbname[?param1 = value1][&param2=value2]... → mysql
  3. user id, passwd 설정
  4. 실제 연결 DriverManager.getConnection (내부적으로 연결)
    Connection conn = DriverManager.getConnection(url, user, passwd);​

 

데이터 읽기

  • DriverManager
    Class.forName("com.mysql.cj.jdbc.Driver");​
  • Connection
    String url = 
    			"jdbc:mysql://localhost:3306/sqldb?characterEncoding=UTF-8&serverTimezone=UTC";
    			String user = "root";
    			String passwd = "1234";
    			Connection conn = DriverManager.getConnection(url, user, passwd);​
  • Statement
    • statement의 팩토리 메소드를 connection이 가지고 있음
    • 객체 생성을 대신해주는 일반 메소드: 팩토리 메소드
      Statement stmt = conn.createStatement()
    • statement 객체를 가지고 올 수 있다. 
  • ResultSet
    • 추출된 데이터 집합을 하나씩 읽어 옴
    • ReultSet rs = stmt.excuteQurey("SELECT ename, sal FROM emp);
    • resultSet 객체에서 값 들고오기
      • next() : 첫번째 값 가르킴
      • 최초의 집합에서 0번째 줄 가리키고 있음
  • 커넥션 반환하기
    • rs.close()
    • stmt.close()
    • conn.close()
      • 다른 프로그램의 connection 요청 못 받을 수도 있음, connection꺼줘야 한다.

 

package mysql.level1;

import java.sql.Statement;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;


public class SelectEmp {
	public static void main(String[] args) {
		
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		}
		catch (ClassNotFoundException cnfe) {
			System.out.println("해당 클래스를 찾을 수 없습니다." + cnfe.getMessage());
		}
		String url = "jdbc:mysql://localhost:3306/sqldb?characterEncoding=UTF-8&serverTimezone=UTC";
		String user = "root";
		String passwd = "1234";
		Connection conn = null;
		Statement stmt = null;
		ResultSet rs = null;
		try {
			conn = DriverManager.getConnection(url, user, passwd);
			stmt = conn.createStatement();
			rs = stmt.executeQuery("select ename, sal, hiredate from emp");
			while(rs.next()) {
				System.out.println(rs.getString("ename") + ","+rs.getDate("hiredate") + "," + rs.getInt("sal"));
			}
		}catch(SQLException se1) {
			System.out.println(se1.getMessage());
		}finally {	//	생성된 객체 close
			try {
				if(rs!= null)
					rs.close();
				if(stmt!= null)
					stmt.close();
				if(conn != null)
					conn.close();
			}catch(SQLException se2) {
				System.out.println(se2.getMessage());
			}
		}
	}
}

 

  • conn 인터페이스를 구현하고 있는 자식의 객체를 반환한다.
    conn = DriverManager.getConnection(url, user, passwd);​
     
    • com.mysql.cj.jdbc.ConnectionImpl
  • executeQuery
    • select 반환 값 DB 서버에 저장소에 들어있음
    • 반환값으로 ResultSet 객체 반환
  • executeUpdate
    • Int 타입 값 반환
      • insert, delete, update : 건수 반환
      • create, drop : -1반환
    • select 구문 제외한 다른거 사용할 때

 

select절에 나온 값 두 가지로 할 수 있다. 

  • rs.getString("ename") 
  • rs.getString(1)

 

 

'study > JAVA 전문가' 카테고리의 다른 글

[JDBC] 방명록  (0) 2021.12.21
JDBC 2  (0) 2021.12.21
mysql 5  (0) 2021.12.20
mysql 4 - 연습문제  (0) 2021.12.20
Mysql 1 - 연습문제  (0) 2021.12.18
  • join
    • 2개의 분산테이블에 있는 여러 컬럼 사용
    • ex) 맥시코에 사는 사원의 이름과 팀장 이름
  • 서브 쿼리
    • 두 개의 쿼리로 가능한거면
    • 특정 컬럼 안에서만 사용
    • ex) 맥시코에  사는 사원

 

셀프 조인

  • 실제 하나지만 두 개 테이블로 간주
  • 이름 다르게 해줘야함

 

SQL

mysql

  • 이체 작업
    • 뺀 만큼 마이너스, 넣은 만큼 플러스가 되어져야 하는 게 한 덩엉리에 되어져야한다. 
    • 두 작업이 모두 실패하거나, 성공하거나

-> 하나의 트랜잭션으로 묶는다. 

  • 무결한 데이터 처리 

 

  • 변화를 반영한다. 
    • 커밋한다. 
    • 최종적으로 반영하겠어. 
  • 지금부터 트랜잭션 시작이야라고 알려야함
    • 명시 안하면 DML 명령 수행할 때 마다 자동 커밋됨. (mysql 특징)
    • 명시하면 취소 가능 (올백)
  • 되돌려야겠어.
    • 올백

 

DDL

  • 트랜잭션이와 관련 X
  • 무조건 커밋 -> 만들어라고하면 만들어짐 

insert (create)

  • 없었던 행 추가
  • 열이름 생략될 경우, values다음에 나오는 값들의 순서 및 개수가 동일해야함
  • 자동으로 증가하는 AUTO_INCREMENT
    • 데이터를 집어넣을 때 없는 컬럼이라고 생각해도 된다. 
    • 숫자 형식만 가능
  • values대신에 select명령
    • 이미 만들어진 테이블에 입력
  • 에러나면 그 이후 처리 안 함
    • insert ignore 사용하면 무시하고 넘어감
  • 이미 존재하는 얘면 수정,

 

update (new)

  • 이미 존재하는 컬럼 변경하는 것
  • where절 생략되면 테이블 전체 행 내용 변경 됨
  • 올백하면 복구할 수 있음, 

 

delete

  • 테이블만 남겨두고 조건된 행 삭제(내용만 삭제)
  • drop table : 테이블 자체 삭제
  • where절 없으면 전체 데이터 삭제
  • 트랜잭션 사용 가능 : 로그 작업
  • truncate : 트랜잭션 적용 X
    • 삭제되면 끝, 복구 불가
    • 테이블 구조 남겨놓고 싶으면 효율적

 

with절

  • CTE를 표현하기 위한 구문
    • 일시적인 뷰 ( 수행하는 동안만 )
      • 뷰 
        • 저장소를 가지고 있지 않음
        • 자주 쓰는 selet명령이라고 생각하면 됨
        • 만들어놓고 계속 재활용할 수 있음
        • 복잡한 sql을 간략하게 하기 위해서 
        • 보안적
          • 뷰를 통해서만 가져갈수 있도록, 
          • 개발자들은 뷰만 쓸 수 있도록
          • 금융권에서 많이 사용함
        • select * from (뷰); 
          • 뷰를 테이블이라고 생각해도 무방

 


mysql의 데이터 형식

  • 숫자 데이터 형식
    • 정수 & 실수 : DECIMAL
  • 문자 데이터 형식
    • char(n) : 고정길이 문자형
      • 남은 길이는 공백으로 들어감
      • n : 문자 갯수
    • varchar(n) : 가변길이 문자형
      • 남은 공간은 없는 공간으로 취급
  • 날짜와 시간 데이터 형식
    • date
    • datetime 
  • 텍스트
    • longtext : 큰 텍스트 파일
    • longblob : 동영상 파일, 큰 바이너리 파일

 

데이터 형식과 형 변환

  • 내부 형 변환
  • 문자는 0으로 변환
    • select 0 = 'mega2', 결과 : 0
    • select 1 > '2mega', 결과 : 0

 

  • 암시적인 형 변환
    • cats() : 형변환하는 대상 as 타입
    • convert() " 대방 , 타입 길이

 


테이블 생성

  • auto_increment 는 primary key여야 한다.
  • 컬럼명 리스트 없으면 넣은 것 그대로 넣겠다. 
    • insert into usertbl values('---', '---', ,,,,)
  • 집어 넣을 값 없으면 null

 

제약조건

  • primary key 제약조건 
    • 행들 구별 할 수 있는 식별자 역활
    • primary key로 설정된 얘는 자동으로 index가 설정됨
  • foreign key
    • 가지고 있는 값 정해져 있다. 
    • on delect cascade 또는 ON UPDATE CASCADE
      • 참조하는 얘가 사라지면 나도 사라짐
      • ex) 게시판 댓글 
    • add, modify 상요해서 생성
  • unique 제약
    • 중복된 값 저장 X
    • null값 허용
      • 입력하지 않아도 되는데, 입력하면 유니크 해야한다.
  • check 제약 조건
    • mysql 8.부터 지원
    • 데이터 넣고 변경할 때마다, 이 컬럼에 저장하기 적합한 값인가를 본다. 
  • default 제약조건
    • 안 넣으면 자동으로 default값이 됨
    • null이 될 수 밖에 없는 상황에서 default값이 넣어짐
    • 값 넣어야 하는 부분에 안 넣었을 때 

 

  • 데이터 무결성을 위한 제약 조건
    • null 값 허용
      • primay key는 자동으로 not null
      • 공백과 0과 다름

 

테이블 수정

  • 열 추가 add, modify
  • 열 삭제 drop
  • chang column : 타입 바꾸기
  • 제약조건 수정
    • drop primary key
      • 하나의 테이블에 primary key 하나만 가능

 

'study > JAVA 전문가' 카테고리의 다른 글

JDBC 2  (0) 2021.12.21
JDBC  (0) 2021.12.20
mysql 4 - 연습문제  (0) 2021.12.20
Mysql 1 - 연습문제  (0) 2021.12.18
조인  (0) 2021.12.17

  • 세로로 묶는거 union
  • 가로로 묶는거 join
    • 아무행이나 붙이는 거 : cross join
  • 테이블 수 -1 만큼의 조인 조건이 있어야함.
  • 두 개 이상인 테이블 하나의 결과 집합으로 만들어 냄
  • 직접적인 관계가 있는 경우에 많이 씀
nc join
표준화된 규격
  1. from table1 join table2 -> 표준화된 규격

 

on 

  • 조인 조건 자유롭게 줄 수 있다.
  • 동일한 얘들끼리 : 등가조인

using

  • 등가조인을 할 경우, 그 때 사용하는 테이블이 똑같을 때
  • 조인 조건하는 컬럼명이 똑같을 때

inner join

  • 일치하는 것 만 
  • 일치하는게 없으면 빼는 것
  • 기본이라서 생략 많이 함

outer join

  • 일치하지 않아도 포함하고 싶을 때, 
  • left, right, full
    • left [outer] join
    • mysql -> full outer join 지원 X
      • left outer join, right outer join union해야함
      • left, rigth적으면 자동으로 outer 조인이라고 생각함
    • 왼쪽 테이블 기준 - left join
    • 오른쪽 테이블 기준 - rigth join
select ename, emp.deptno, dname
from emp
left join dept
on emp.DEPTNO = dept.DEPTNO;
select ename, emp.deptno, dname
from emp
right join dept
on emp.DEPTNO = dept.DEPTNO;

 

full outer join 지원 안 되니깐.

select ename, emp.deptno, dname
from emp
left join dept
on emp.DEPTNO = dept.DEPTNO
UNION
select ename, emp.deptno, dname
from emp
right join dept
on emp.DEPTNO = dept.DEPTNO;

union사용하면 된다. 

 


cross join 

다 만나는 것


select * from emp join dept on emp.deptno = dept.deptno;

emp 테이블 14명이 deptno의 값을 dept값으로 매칭시키겠다. 

  1. emp : 기준테이블
  2. dept : 조인 테이블

  • dept 테이블 친구들이 emp에 붙는다
  • dept 열이 null인 친구 제외 - inner join
  • 사용할 때, 어느 테이블에 있는 DEPTNO인지 명시해줘야한다. (DEPTNO가 두 개
    • 테이블 별로 각자 들어가는 것

 

SELECT * FROM emp JOIN dept USING (deptno);

DEPNO 열이 하나만 나온다. 

 


on

SELECT ename, emp.deptno, dname
FROM emp
JOIN dept
ON emp.deptno = dept.deptno;

어느것에 있는 deptno인지 명시해줘야한다. 

SELECT ename, deptno, dname	--에러난다.
FROM emp
JOIN dept
ON emp.deptno = dept.deptno;

 

using

SELECT ename, deptno, dname
FROM emp
JOIN dept
USING (deptno);

 


직원들이 근무하는 부서명과 지역(도시) 정보 출력

using

select ename, dname, city
from emp
join dept
using (deptno)
join locations
using (loc_code);

on

SELECT ename, dname, city
FROM emp e
JOIN dept d
ON e.deptno = d.deptno
JOIN locations l
ON d.loc_code = l.loc_code;

테이블 별칭써도 됨. 

 


직원들이 근무하는 지역(도시) 정보 출력

SELECT ename, city
FROM emp e
JOIN dept
USING (deptno)
JOIN locations
using(loc_code);
SELECT ename, city
FROM emp e
JOIN dept d
ON e.DEPTNO = d.DEPTNO
JOIN locations l
ON d.LOC_CODE = l.LOC_CODE;

 


on절만 사용 가능 -> between 사용 (and)

SELECT ename, sal, grade 
FROM emp e
JOIN salgrade s
ON e.sal BETWEEN s.losal and s.hisal;

어떤 범위에 속하는가

SELECT ename, sal, concat(grade,"등급") 등급 
FROM emp e
JOIN salgrade s
ON e.sal >= s.losal AND e.sal <= s.hisal;

 


 

'study > JAVA 전문가' 카테고리의 다른 글

mysql 4 - 연습문제  (0) 2021.12.20
Mysql 1 - 연습문제  (0) 2021.12.18
mysql 3 - 연습문제  (0) 2021.12.17
mysql 3  (0) 2021.12.17
DBMS  (0) 2021.12.15

GROUP BY

  • 모든 단위는 그룹 단위로 나옴
  • group by 안 써도 집계 함수 쓸 수 있다.
    • 주로 쓰이는 게 group by라서 그렇지
  • 기준이 됐던 칼럼 명 나타내 줘야 함 옆에 - 보기 좋음
  • 그룹핑해서 select절에 올 수 있는 행이 제한되어있다.
    • ename(일반 컬럼) 같은 거 못 옴
    • 그룹핑하는데 기준이 된 칼럼,칼럼에 대한 식, 집계함수집계 함수만 올 수 있음
      • 열 단위로 카디널리티 개수가 같아야 해서
  • ORDER BY 안 해도 됨 -> 원래 정렬되어 있음
    SELECT deptno, avg(sal) from emp GROUP BY deptno;​
    부서가 정해지지 않은 사람들도 그룹으로
  • is not null
    select deptno, sum(sal) from emp where deptno is not null group by deptno;
     카디널리티 : 그룹 단위의 행
    1. from 문
    2. where절
    3. group by 절
  • count
    • count(*) -> 행의 개수 (null 상관없이 개수 세기)
    • count(특정 칼럼 명) -> null이 아닌 얘들 개수 세줌

 

  • 뒤에 올 수록 서브 칼럼 
    20번 일하는 직원 중 'CLERK' job인 직원은 1명이다.
  • select deptno, job, count(*) from emp where deptno is not null group by deptno, job;​

 

Having절

  • 어떤 조건을 충족하지 못하는 건 제외
    • 행 단위로 읽어올 때 -> where절 (행에 대한 조건, from 다음에 실행)
    • 그룹으로 나눈 다음에 그룹에 대한 조건 -> having (그룹에 대한 조건, 그룹 다음에 실행)

 

 

ROLLUP

  • 각 그룹 단위의 총합계 내줌
    • 소 합계 -> 총합계 
      select ifnull(job,'합계') 직무, sum(sal) '급여' from emp group by job with rollup;​
    • select job, sum(sal) '급여' from emp group by job with rollup;​
  • 보충
    select ifnull(job,"직원 별 합계") 잡, ifnull(deptno,"부서 별 합계"), count(*)
    from emp
    where deptno is not NULL
    group by job, DEPTNO
    with rollup;​
    부서가 null이 아닌 직원, 부서별 합계

 

Set

union 모두 포함 (중복 한번만)
union all 모두 포함 (중복 결과 모두 표현)
intersect 모두 포함한 행만 표현
minus 쿼리 1 - 쿼리 2
  • intersect, minus는 mysql에서 지원 안 함. 
  • 추출되는 컬럼의 개수가 같아야함
    • select 순서를 다르게 하면, 에러는 안 나지만 논리적 문제가 발생함 (자동으로 안 바꿔줌)
  • union
    select ename, hiredate from emp where year(hiredate) = 1981
    UNION
    select ename, hiredate from emp where deptno = 30;​

 

  • union all
    select ename, hiredate from emp where year(hiredate) = 1981
    UNION all
    select ename, hiredate from emp where deptno = 30;​

'study > JAVA 전문가' 카테고리의 다른 글

조인  (0) 2021.12.17
mysql 3 - 연습문제  (0) 2021.12.17
DBMS  (0) 2021.12.15
inner  (0) 2021.12.10
자료구조 2 - 복습  (0) 2021.12.10

+ Recent posts