คำอธิบาย

วิธีถัดไปในการจัดเก็บลำดับชั้นของคลาสคือการจัดเก็บคลาสทั้งหมดในลำดับชั้นไว้ในตารางเดียว กลยุทธ์นี้เรียกว่าSingle Table

ตัวอย่างเช่น:

CREATE TABLE user_ employee_client {
  id INT,
  name VARCHAR,
  birthday DATE,
  occupation VARCHAR,
  salary INT,
  join DATE,
  address VARCHAR,
  DTYPE VARCHAR
}

นั่นคือเรามีตารางเดียวซึ่งคอลัมน์สำหรับทุกชั้นในลำดับชั้นของเราถูกทำเครื่องหมายด้วยสีที่ต่างกัน นอกจากนี้ยังมีคอลัมน์บริการพิเศษDTYPE VARCHARโดยที่ Hibernate จะจัดเก็บชื่อของคลาสเอนทิตี

สิ่งเดียวที่ต้องทำคืออธิบายให้ Hibernate ทราบว่าตอนนี้ข้อมูลของคลาส Entity ถูกจัดเก็บไว้ในฐานข้อมูลในตารางเดียว สามารถทำได้โดยใช้ คำอธิบายประกอบ @Inheritance :

@Inheritance(strategy = InheritanceType.SINGLE_TABLE)

ตัวอย่างชั้นเรียนของเรา:

@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@Entity
class User {
  int id;
  String name;
  LocalDate birthday;
}
@Entity
class Employee extends User {
 	String occupation;
 	int salary;
 	LocalDate join;
}
@Entity
class Client extends User {
   String address;
}

วิธีการจัดเก็บข้อมูล

ตอนนี้ลองเขียนตัวอย่างที่เราสร้างเอนทิตีสองสามรายการแล้วบันทึกลงในฐานข้อมูล:

Employee employee = new Employee();
employee.id = 101;
employee.name = "Ivanov";
employee.birthday = LocalDate.of("01-01-1999");
employee.occupation = "Programmer"
employee.salary = 100000;
employee.join = LocalDate.of("12-01-2018");
session.persist(employee);

Client client = new Client();
client.id = 102;
client.name = "Petrov";
client.birthday = LocalDate.of("15-11-1988");
client.address = "Shandara";
session.persist(client);

เมื่อบันทึกลงในฐานข้อมูล แบบสอบถาม SQL ต่อไปนี้จะถูกดำเนินการ:

INSERT INTO user_ employee_client (id, name, birthday, occupation, salary, join, DTYPE)
VALUES (101, 'Ivanov', '01-01-1999', 'Programmer', 100000, '12-01-2018', 'Employee')

INSERT INTO user_ employee_client (id, name, birthday, address, DTYPE)
VALUES (102, 'Petrov', '15-11-1988', 'Shandara', 'Client')

เมื่อบันทึกข้อมูลลงในตาราง ไฮเบอร์เนตจะส่งเฉพาะฟิลด์เอนทิตีที่รู้จักเท่านั้น ซึ่งหมายความว่าคอลัมน์ที่ไม่ได้ระบุจะเป็น NULL

และนั่นหมายความว่าคุณไม่สามารถระบุประเภท ไม่เป็นโมฆะ สำหรับคอลัมน์อาชีพได้ เนื่องจากเมื่อไคลเอนต์ถูกจัดเก็บไว้ในตารางเดียวกัน อาชีพของเขาจะเป็นโมฆะ นี่เป็นข้อเสียประการหนึ่งของการจัดเก็บเอนทิตีที่แตกต่างกันในตารางเดียวกัน

ฟิลด์สุดท้ายในแบบสอบถาม SQL คือคอลัมน์ DTYPE ซึ่งมีชื่อของคลาสเอนทิตี Hibernate ใช้เมื่อคุณต้องการอ่านข้อมูลจากตารางของคุณ

ตัวอย่าง:

List<User> accounts = session.createQuery("from User").list();

แบบสอบถามนี้จะส่งคืนรายการของวัตถุประเภทผู้ใช้ทั้งหมดที่จัดเก็บไว้ในฐานข้อมูล ได้แก่ ผู้ใช้ พนักงาน และไคลเอนต์ ตามคอลัมน์ DTYPE ประเภทเอนทิตีจะถูกกำหนดอย่างถูกต้อง และจะสร้างออบเจกต์ของคลาสที่ถูกต้อง

ในกรณีของเรา จะมีวัตถุสองรายการในรายการบัญชี: ประเภทพนักงานและประเภทลูกค้า

กฎ HQL