将派生类存储在数据库中的良好实践

时间:2014-03-17 16:42:33

标签: java mysql database data-structures

我正在编写一个简单的Java应用程序(用于研究目的)来管理员工,我需要一个建议:如何从数据库中存储和检索数据。

我到目前为止所写的代码太大了,无法用它来表达,所以,用两个词来说:

我有下一个层次结构: 抽象类员工:4个属性,getter,setter class Salaried:2个新属性 每小时:2个新属性 class Director:3个新属性 班级经理:1个新属性

我有一个包含1个表的MySQL数据(创建脚本):

CREATE TABLE `employee` (
  `SSN` int(9) NOT NULL PRIMARY KEY,
  `FirstName` varchar(20) NOT NULL,
  `LastName` varchar(20) NOT NULL,
  `Department` varchar(20) NOT NULL,
  `Salary` float(10) NULL,
  `OvertimeHours` float(10) NULL,
  `HourlyWage` float(10) NULL,
  `NumberHours` float(10) NULL,
  `Organization` varchar(30) NULL,
  `Bonus` float(10) NULL
);

前4个字段适用于所有员工。

薪水 OvertimeHours 薪水类的属性

HourlyWage NumberHours 每小时类的属性

薪水奖金组织导演类的属性

薪水也是经理类的一个属性

我已经创建了一个静态类数据库来使用MySQL。

import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.Connection;


public abstract class Database {
    // constants
    private static final String DRIVER = "com.mysql.jdbc.Driver";
    private static final String DBNAME = "records";
    private static final String DBUSER = "root";
    private static final String DBPASS = "";
    private static final String CONURL = "jdbc:mysql://localhost/" + DBNAME;

    // class attributes
    private static Connection connection = null;


    public static boolean fillEmployee(Employee emp, int ssn)
    {
        try {
            PreparedStatement stm = connection.prepareStatement(
                "SELECT FirstName, LastName, Department "
              + "FROM employee "
              + "WHERE SSN = ?"
            );

            stm.setInt(1, ssn);

            ResultSet rs = stm.executeQuery();

            if(!rs.next())
                return false;

            emp.setSocialSecurity(ssn);
            emp.setFirstName(rs.getString("FirstName"));
            emp.setLastName(rs.getString("LastName"));
            emp.setDepartment(rs.getString("Department"));

            stm.close();
            rs.close();

        } catch (Exception e) {
            System.out.println(e.getMessage());
            System.exit(0);
        }
        return true;
    }


    public static boolean deleteEmployee(int ssn){
        try {
            PreparedStatement stm = connection.prepareStatement(
                "DELETE "
              + "FROM employee "
              + "WHERE SSN = ?"
            );

            stm.setInt(1, ssn);
            return (stm.executeUpdate() == 1);

        } catch (Exception e) {
            System.out.println(e.getMessage());
            System.exit(0);
        }
        return false;
    }


    // class methods
    public static Salaried getSalariedEmployee(int ssn){
        Salaried employee = new Salaried();
        try {

            if(!fillEmployee(employee, ssn))
                return null;

            PreparedStatement stm = connection.prepareStatement(
                "SELECT Salary, OvertimeHours "
              + "FROM employee "
              + "WHERE SSN = ?"
            );

            stm.setInt(1, ssn);
            ResultSet rs = stm.executeQuery();

            employee.setSalary(rs.getFloat("Salary"));
            employee.setOvertimeHours(rs.getFloat("OvertimeHours"));

            stm.close();
            rs.close();

        } catch (Exception e) {
            System.out.println(e.getLocalizedMessage());
            System.exit(0);
        }
        return employee;
    }

    public static void createConnection() {
        if (connection !=  null) 
            return;

        try {

            Class.forName(DRIVER);
            connection = DriverManager.getConnection(CONURL, DBUSER, DBPASS);

        } catch (Exception e) {

            System.out.println(e.getMessage());
            System.exit(0);

        }
    }

    public static void closeConnection(){
        if (connection == null) 
            return;

        try{

            connection.close();
            connection = null;

        } catch (Exception e) {

            System.out.println(e.getMessage());
            System.exit(0);

        }
    }
}

您对 getSalariedEmployee fillEmployee 方法有何看法? 如何改进应用程序的整体设计和架构?

3 个答案:

答案 0 :(得分:1)

我认为您可以等待在getSalariedEmployee中创建员工对象。 只有在找到db对象时才实例化它。 因为如果在找不到它时返回null,则仍然会创建employee对象。

答案 1 :(得分:1)

也许你应该从阅读好书Patterns of Enterprise Architecture开始。它有一个很好的章节,涵盖了我们通常处理数据库的不同方式。

您可以在随附网站上阅读这些内容的快速定义:

所有模式都有优点和缺点,其中一些模式有完整的框架可以帮助您为它们编写代码。

答案 2 :(得分:1)

我要做的第一件事就是停止对所有数据库函数使用静态方法。 为什么数据库是一个抽象类?是否有另一个类使用特定实现扩展数据库(如MyDatabase或OracleDatabase。

您可以考虑使用静态方法返回数据库的实例,然后将静态方法转换为公共实例方法。