----------------------------------------------
성적관리 JDBC 프로그램
- JDBC 프로그램 작성은 아래 순서를 따른다.
기능 구현 분석 > 화면 구성 > 데이터베이스(샘플 쿼리) 준비 > 클래스 구성 분석 > 액션 코드 작성 > 테스트
5. 소스 코드 (최종 버전)
//DBConn.java
package com.test;
import java.sql.*;
//데이터베이스 연결 액션 클래스
public class DBConn {
//메소드들 내부에서 공통 사용하는 멤버는
//멤버변수로 등록한다.
//static 키워드 추가
private static Connection conn;
//커넥션 객체 준비 메소드
//-> Singleton
public static Connection getConnection() throws ClassNotFoundException, SQLException {
if (conn == null) {
Class.forName("oracle.jdbc.driver.OracleDriver");
conn = DriverManager.getConnection("jdbc:oracle:thin:username/password@IP주소:1521:xe");;
}
return conn;
}
//마무리 메소드
public static void close() {
try {
if (conn != null) {
conn.close();
}
}catch(Exception e){
}
conn = null;
}
}
//Student.java
package com.test;
//자료형 클래스
public class Student {
//멤버변수 -> 데이터베이스 컬럼명, 출력 항목
//sid, name, tel, gradeCheck
//기본 자료형은 String으로 지정.
private String sid, name, tel;
//성적 입력 여부 확인용
//입력 O -> 1
//입력 X -> 0
private int gradeCheck;
public String getSid() {
return sid;
}
public void setSid(String sid) {
this.sid = sid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getTel() {
return tel;
}
public void setTel(String tel) {
this.tel = tel;
}
public int getGradeCheck() {
return gradeCheck;
}
public void setGradeCheck(int gradeCheck) {
this.gradeCheck = gradeCheck;
}
}
//Grade.java
package com.test;
//자료형 클래스
public class Grade {
//멤버변수 -> 데이터베이스 컬럼명, 출력 항목
//->sid, sub1, sub2, sub3
//->name, tot, ave, grade
//null 자료는 int 자료형 변수에 저장 불가능
//null 자료는 String 자료형 변수에 저장 가능
private String sid, name, sub1, sub2, sub3, tot, ave;
private int grade; //0 합격, 1 과락, 2 불합격
public String getSid() {
return sid;
}
public void setSid(String sid) {
this.sid = sid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSub1() {
return sub1;
}
public void setSub1(String sub1) {
this.sub1 = sub1;
}
public String getSub2() {
return sub2;
}
public void setSub2(String sub2) {
this.sub2 = sub2;
}
public String getSub3() {
return sub3;
}
public void setSub3(String sub3) {
this.sub3 = sub3;
}
public String getTot() {
return tot;
}
public void setTot(String tot) {
this.tot = tot;
}
public String getAve() {
return ave;
}
public void setAve(String ave) {
this.ave = ave;
}
public int getGrade() {
return grade;
}
public void setGrade(int grade) {
this.grade = grade;
}
}
//StudentDAO.java
package com.test;
import java.util.*;
import java.sql.*;
public class StudentDAO {
//학생 명단 출력 메소드
public ArrayList<Student> list() {
ArrayList<Student> result = new ArrayList<Student>();
//1. 데이터베이스 연결
//2. SELECT 쿼리 준비 및 실행
//3. 결과를 컬렉션에 저장
//4. 데이터베이스 연결 마무리
//5. 컬렉션 반환
Connection conn = null;
Statement stmt = null;
try {
conn = DBConn.getConnection();
stmt = conn.createStatement();
//주의: 쿼리 문자열 끝에 ;(semicolon) 없음.
String sql = String.format("SELECT sid, name, tel, gradeCheck FROM studentView ORDER BY sid");
ResultSet rs = stmt.executeQuery(sql);
while(rs.next()) {
//문제)
//데이터베이스 자료를 순차적으로 읽어내서
//Student 객체에 저장하고
//Student 객체를 컬렉션에 저장하는 액션 추가
String sid = rs.getString("sid");
String name = rs.getString("name");
String tel = rs.getString("tel");
int gradeCheck = rs.getInt("gradeCheck");
Student s = new Student();
s.setSid(sid);
s.setName(name);
s.setTel(tel);
s.setGradeCheck(gradeCheck);
result.add(s);
}
rs.close();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (stmt != null) {
stmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result;
}
//학생 수 출력 메소드
public int count() {
int result = 0;
//1. 데이터베이스 연결
//2. SELECT 쿼리 준비 및 실행
//->SELECT COUNT(*) AS "count" FROM student
//3. 결과를 변수에 저장
//4. 데이터베이스 연결 마무리
//5. 변수 반환
Connection conn = null;
PreparedStatement pstmt = null;
try {
conn = DBConn.getConnection();
String sql = String.format("SELECT COUNT(*) AS \"count\" FROM student");
pstmt = conn.prepareStatement(sql);
//바인딩 데이터 연결하는 과정
ResultSet rs = pstmt.executeQuery(); //SELECT 쿼리인 경우
while(rs.next()) {
result = rs.getInt("count");
}
rs.close();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (pstmt != null) {
pstmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result;
}
//학생 추가(입력) 메소드
public int add(Student student) {
int result = 0;
//문제)
//1. 데이터베이스 연결
//2. INSERT 쿼리 준비 및 실행
//-> INSERT INTO student (sid, name, tel)
// VALUES (studentSeq.nextval, ?, ?)
//3. 결과를 변수에 저장
//4. 데이터베이스 연결 마무리
//5. 변수 반환
Connection conn = null;
PreparedStatement pstmt = null;
try {
conn = DBConn.getConnection();
String sql = String.format("INSERT INTO student (sid, name, tel) VALUES (studentSeq.nextval, ?, ?)");
pstmt = conn.prepareStatement(sql); //쿼리를 사전 분석한다.
pstmt.setString(1, student.getName()); //'(작은 따옴표) 추가
pstmt.setString(2, student.getTel()); //'(작은 따옴표) 추가
result = pstmt.executeUpdate();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (pstmt != null) {
pstmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result;
}
//학생 번호 검색 메소드
public Student searchSid(String sid) {
Student result = null;
//문제)
//1. 데이터베이스 연결
//2. SELECT 쿼리 준비 및 실행
//SELECT sid, name, tel, gradeCheck
// FROM studentView
// WHERE sid=?
//3. 결과를 변수에 저장
//4. 데이터베이스 연결 마무리
//5. 변수 반환
Connection conn = null;
PreparedStatement pstmt = null;
try {
conn = DBConn.getConnection();
//검색 액션은 PK 가 지정된 sid 컬럼을 대상으로
//하기 때문에
//검색 결과는 0 또는 1 이다.
//검색 결과가 있다면 Student 객체에 저장해서 반환.
String sql = String.format("SELECT sid, name, tel, gradeCheck FROM studentView WHERE sid=?");
pstmt = conn.prepareStatement(sql);
//바인딩 데이터 연결하는 과정
pstmt.setInt(1, Integer.parseInt(sid));
ResultSet rs = pstmt.executeQuery(); //SELECT 쿼리인 경우
//SELECT 결과가 존재하는 경우
//rs.next() 메소드 결과는 true가 된다.
//-> 반복문 실행 가능
/*
while(rs.next()) {
result = new Student();
}
*/
while(rs.next()) {
String name = rs.getString("name");
String tel = rs.getString("tel");
int gradeCheck = rs.getInt("gradeCheck");
result = new Student();
result.setSid(sid);
result.setName(name);
result.setTel(tel);
result.setGradeCheck(gradeCheck);
}
rs.close();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (pstmt != null) {
pstmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result; //null 또는 Student객체
}
}
//GradeDAO.java
package com.test;
import java.util.*;
import java.sql.*;
public class GradeDAO {
//성적 추가(입력) 메소드
public int add(Grade grade) {
int result = 0;
//문제)
//1. 데이터베이스 연결
//2. INSERT 쿼리 준비 및 실행
//-> INSERT INTO grade (sid, sub1, sub2, sub3)
// VALUES (?, ?, ?, ?)
//3. 결과를 변수에 저장
//4. 데이터베이스 연결 마무리
//5. 변수 반환
Connection conn = null;
PreparedStatement pstmt = null;
try {
conn = DBConn.getConnection();
String sql = String.format("INSERT INTO grade(SID,sub1,sub2,sub3) VALUES(?, ?, ?, ?)");
pstmt = conn.prepareStatement(sql); //쿼리를 사전 분석한다.
pstmt.setString(1, grade.getSid()); //'(작은 따옴표) 추가
pstmt.setInt(2, Integer.parseInt(grade.getSub1()));
pstmt.setInt(3, Integer.parseInt(grade.getSub2()));
pstmt.setInt(4, Integer.parseInt(grade.getSub3()));
result = pstmt.executeUpdate();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (pstmt != null) {
pstmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result;
}
//성적 출력 메소드
public ArrayList<Grade> list() {
ArrayList<Grade> result = new ArrayList<Grade>();
//문제)
//1. 데이터베이스 연결
//2. SELECT 쿼리 준비 및 실행
//SELECT sid, name, sub1, sub2, sub3
// , tot, ave, grade
// FROM gradeView
// ORDER BY sid;
//3. 결과를 컬렉션에 저장
//4. 데이터베이스 연결 마무리
//5. 컬렉션 반환
Connection conn = null;
Statement stmt = null;
try {
conn = DBConn.getConnection();
stmt = conn.createStatement();
//주의: 쿼리 문자열 끝에 ;(semicolon) 없음.
String sql = String.format("SELECT sid, name, sub1, sub2, sub3, tot, ave, grade FROM gradeView ORDER BY sid");
ResultSet rs = stmt.executeQuery(sql);
while(rs.next()) {
String sid = rs.getString("sid");
String name = rs.getString("name");
String sub1 = rs.getString("sub1");
String sub2 = rs.getString("sub2");
String sub3 = rs.getString("sub3");
String tot = rs.getString("tot");
String ave = rs.getString("ave");
int grade = rs.getInt("grade");
Grade g = new Grade();
g.setSid(sid);
g.setName(name);
g.setSub1(sub1);
g.setSub2(sub2);
g.setSub3(sub3);
g.setTot(tot);
g.setAve(ave);
g.setGrade(grade);
result.add(g);
}
rs.close();
}catch(Exception e){
e.printStackTrace();
}finally{
try {
if (stmt != null) {
stmt.close();
}
}catch(Exception e){
}
DBConn.close();
}
return result;
}
}
//MenuAction.java
package com.test;
import java.util.*;
//콘솔 액션 O. 데이터베이스 관련 액션 코드 X.
public class MenuAction {
//StudentDAO, GradeDAO 객체 준비 -> 생성자
private StudentDAO sdao;
private GradeDAO gdao;
public MenuAction() {
sdao = new StudentDAO();
gdao = new GradeDAO();
}
//1. 학생 입력
public void menu1(Scanner sc) {
//이름, 전화번호를 외부 입력 받아서
//데이터베이스에 저장하는 액션
System.out.print("이름 전화번호?");
String name = sc.next();
String tel = sc.next();
Student student = new Student();
student.setName(name);
student.setTel(tel);
int result = sdao.add(student);
System.out.printf("%d개의 행이 삽입되었습니다.%n", result);
}
//2. 성적 입력 (학생 검색)
public void menu2(Scanner sc) {
System.out.print("학생 번호 검색(x exit)?");
String sid = sc.next();
if (!sid.equalsIgnoreCase("x")) {
Student student = sdao.searchSid(sid);
if (student == null) {
System.out.println("검색 결과가 없습니다.");
} else {
System.out.printf("%s %s %s %s%n", student.getSid(),
student.getName(), student.getTel(),
(student.getGradeCheck() == 1) ? "O" : "X");
if (student.getGradeCheck() == 1) {
System.out.println("이미 성적이 입력된 상태입니다.");
} else {
// System.out.println("성적 입력 가능....");
System.out.print("과목1 과목1 과목1?");
String sub1 = sc.next();
String sub2 = sc.next();
String sub3 = sc.next();
Grade grade = new Grade();
grade.setSid(sid);
grade.setSub1(sub1);
grade.setSub2(sub2);
grade.setSub3(sub3);
int result = gdao.add(grade);
System.out.printf("%d개의 행이 삽입되었습니다.", result);
}
}
}
}
//3. 학생 출력
public void menu3() {
//인원수 및 학생 명단 출력
System.out.printf("전체 학생 수 : %d명%n", sdao.count());
System.out.println("------------------------");
System.out.println("SID NAME TEL GRADECHECK");
System.out.println("------------------------");
for (Student s : sdao.list()) {
System.out.printf("%s %s %s %s %n"
, s.getSid()
, s.getName()
, s.getTel()
, (s.getGradeCheck()==1)?"O":"X" );
}
}
//4. 성적 출력
public void menu4() {
//인원수 및 성적 출력
String[] gradeArray = {"합격", "과락", "불합격"};
System.out.printf("전체 학생 수 : %d명%n", sdao.count());
System.out.println("------------------------");
System.out.println("SID NAME SUB1 SUB2 SUB3 TOT AVE GRADE");
System.out.println("------------------------");
for (Grade grade : gdao.list()) {
System.out.printf("%s %s %s %s %s %s %s %s%n"
, grade.getSid()
, grade.getName()
, grade.getSub1()
, grade.getSub2()
, grade.getSub3()
, grade.getTot() //총점
, (grade.getAve()==null)?grade.getAve():String.format("%.1f", Double.parseDouble(grade.getAve())) //평균. 소수 이하 1자리 지정. 문자열->실수. NULL 값은 제외.
, gradeArray[grade.getGrade()]); //판정. 0 합격, 1 과락, 2 불합격
}
}
}
//Main.java
package com.test;
import java.util.*;
//메인 메뉴 액션 클래스
public class Main {
public static void main(String[] args) {
MenuAction menu = new MenuAction();
Scanner sc = new Scanner(System.in);
do {
System.out.println("--- 성적 관리(ORACLE) ---");
System.out.println("1. 학생 입력");
System.out.println("2. 성적 입력 (학생 검색)");
System.out.println("3. 학생 출력");
System.out.println("4. 성적 출력");
System.out.print("선택(1~4, 0 종료)?");
int m = sc.nextInt();
if (m==0) {
break;
}
switch (m) {
case 1: menu.menu1(sc); break;
case 2: menu.menu2(sc); break;
case 3: menu.menu3(); break;
case 4: menu.menu4(); break;
}
System.out.println();
}while(true);
sc.close();
}
}
-----------------------------------
성적관리 완성됨.