2009-01-06 17 views
5

Para una asignación de base de datos, tengo que modelar un sistema para una escuela. Parte de los requisitos es modelar información para el personal, los estudiantes y los padres.Modelado de herencia en una base de datos

En el diagrama de clases UML he modelado esto como esas tres clases que son subtipos de un tipo de persona. Esto se debe a que todos requerirán información sobre, entre otras cosas, datos de dirección.

Mi pregunta es: ¿cómo modelar esto en la base de datos (mysql)?

pensamientos hasta el momento son los siguientes:

  1. Crear una tabla persona monolítica que contiene toda la información para cada tipo y tendrá un montón de valores nulos dependiendo de qué tipo se está almacenando. (Dudo que esto caiga bien con el conferenciante a menos que argumente el caso muy convincentemente).
  2. Una tabla de personas con tres claves externas que hacen referencia a los subtipos pero dos de las cuales serán nulas. De hecho, ni siquiera estoy seguro de si eso tiene sentido o si es posible.
  3. De acuerdo con esta wikipage about django que es posible implementar la clave principal en los subtipos de la siguiente manera:

    "id" integer NOT NULL PRIMARY KEY REFERENCES "supertype" ("id")
  4. algo más que no he pensado en ...

Así que para aquellos que tienen herencia modelada en una base de datos anterior; ¿Cómo lo hiciste? ¿Qué método recomiendas y por qué?

Los enlaces a los artículos/publicaciones en el blog o las preguntas anteriores son más que bienvenidas.

¡Gracias por su tiempo!

ACTUALIZACIÓN

Alright Gracias por las respuestas a todos. Ya tenía una tabla de direcciones por separado, así que eso no es un problema.

Saludos,

Adam personal

+0

Si esta es una tarea añadir la etiqueta de la tarea favor – JoshBerke

+0

También puedes ver: http://stackoverflow.com/questions/5802/inheritance-in-database – JoshBerke

+0

Ok seguro. Supongo que está permitido hacer preguntas relacionadas con las tareas si no le pido a la gente que lo haga todo por mí. –

Respuesta

5

4 mesas, estudiantes, padres y persona para el material genérico. El personal, los estudiantes y los padres tienen claves de forign que cada referencia a la persona (no al revés).

La persona tiene un campo que identifica cuál es la subclase de esta persona (es decir, el personal, el alumno o el padre).

EDIT:

Como ha señalado HLGM, direcciones debe existir en una mesa separada, ya que cualquier persona puede tener varias direcciones. (Sin embargo, estoy a punto de estar en desacuerdo conmigo mismo, es posible que desee restringir deliberadamente las direcciones a una por persona, limitando las opciones de listas de correo, etc.).

+0

Cinco tablas realmente como dirección deben ser una tabla separada, así como las personas tienen varias direcciones – HLGEM

+0

@HLGEM: Esto es cierto –

+0

¿sería una buena idea hacer que las claves externas en las claves heredadas de las clases primarias? – CaptainProton

1

"Así que para aquellos que han modelado la herencia en una base de datos antes;?? ¿Cómo lo haces ¿Qué método me recomienda y por qué "

Métodos 1 y 3 son buenos. Las diferencias son principalmente en lo que son sus casos de uso.

1) adaptabilidad: ¿qué es más fácil de cambiar? Varias tablas separadas con relaciones FK a la tabla primaria.

2) rendimiento - ¿qué requiere menos combinaciones? Una sola mesa.

Ratas. Ningún diseño logra ambos.

Además, hay un tercer diseño además de su mono-tabla y FK-parental.

Tres tablas separadas con algunas columnas comunes (por lo general, copiar y pegar las columnas de la superclase entre todas las tablas de las subclases). Esto es muy flexible y fácil de trabajar. Pero, requiere una unión de las tres tablas para armar una lista general.

2

Bueno, creo que todos los enfoques son válidos y cualquier conferenciante que marque para empujarlo en una tabla (a menos que los requisitos sean específicos para decir que no debería) es eliminar una estrategia viable debido a su propia opinión personal.

Le recomiendo que revise la documentación de NHibernate, ya que proporciona diferentes enfoques para realizar lo anterior. Lo cual ahora intentaré pobremente loro.

Sus opciones:

  • 1) Una tabla con todos los datos que tiene una columna "delimitador". Esta columna indica qué tipo de persona es la persona. Esto es viable en escenarios simples y (gravemente) alto rendimiento donde las uniones dañarán demasiado
  • 2) Tabla por clase que conducirá a la duplicación de columnas pero evitará uniones nuevamente, por lo que es simple y un poco más rápida (aunque solo un lil e indexación mitiga esto en la mayoría de los escenarios).
  • 3) Herencia heredada. La versión normalizada. Ya casi estás ahí, pero tu llave está en el lugar equivocado IMO. Su tabla de empleados debe contener una PERSONID por lo que puede hacer:

    seleccione employee.id, person.name del empleado en combinación interna persona employee.personId = person.personId

Para obtener todos los nombres de empleados donde el nombre solo se especifica en la tabla de personas.

0

Las bases de datos OO pasan por lo mismo y ofrecen prácticamente las mismas opciones.

Si se trata de modelar subclases en una base de datos, probablemente ya esté pensando en las soluciones que he visto en bases de datos OO reales (dejando los campos vacíos).

De lo contrario, podría pensar en crear un sistema que no use la herencia de esta manera.

La herencia siempre se debe usar con moderación, y este es probablemente un caso bastante malo.

Una buena pauta es nunca usar herencia a menos que realmente tenga un código que haga cosas diferentes al campo de una clase "Parent" que al mismo campo en una clase "Child". Si el código comercial de su clase no se refiere específicamente a un campo, ese campo no debería causar herencia en absoluto.

Pero de nuevo, si estás en la escuela, puede que no coincida con lo que están tratando de enseñar ...

2

Me gustaría ir por el n. ° 3.

Su objetivo es impresionar a un conferenciante, no a un PM o cliente. Los académicos tienden a rechazar los nulos y pueden (de manera subconsciente) penalizarlo por usar los otros métodos (que se basan en nulos).

Y no necesita necesariamente esa extensión django (TECLA PRIMARIA ... REFERENCIAS ...) Usted podría usar una LLAVE EXTRAÑA EXTRAORDINARIA para eso.

0

La respuesta "correcta" a los efectos de una asignación es probablemente # 3:

Person 
PersonId Name Address1 Address2 City Country 

Student 
PersonId StudentId GPA Year .. 

Staff 
PersonId StaffId Salary .. 

Parent 
PersonId ParentId ParentType EmergencyContactNumber .. 

Dónde PERSONID es siempre la clave primaria, y también una clave externa en los últimos tres tablas.

Me gusta este enfoque porque hace que sea fácil representar a la misma persona que tiene más de un rol. Un maestro también podría ser un padre, por ejemplo.

0

que sugieren cinco mesas persona Estudiante personal Padres Dirección

por qué - porque la gente puede tener múltiples addesses y las personas también pueden tener múltiples funciones y la información que desea para el personal es diferente de la información que necesidad de almacenar para padres o estudiantes.

Además, es posible que desee guardar el nombre como last_name, Middle_name, first_name, Name_suffix (como jr.) En lugar de simplemente como nombre. ¡Créeme, querrás poder buscar en last_name! El nombre no es único, por lo que deberá asegurarse de tener una clave primaria sustituta única.

Lea acerca de la normalización antes de tratar de diseñar una base de datos. Aquí es una fuente para empezar: http://www.deeptraining.com/litwin/dbdesign/FundamentalsOfRelationalDatabaseDesign.aspx

0

persona Super debe ser creado de esta manera:

CREATE TABLE Person(PersonID int primary key, Name varchar ... etc ...) 

Todos los tipos Sub deben ser creados de esta manera:

CREATE TABLE IF NOT EXISTS Staffs(StaffId INT NOT NULL , 
    PRIMARY KEY (StaffId) , 
    CONSTRAINT FK_StaffId FOREIGN KEY (StaffId) REFERENCES Person(PersonId) 
) 

CREATE TABLE IF NOT EXISTS Students(StudentId INT NOT NULL , 
    PRIMARY KEY (StudentId) , 
    CONSTRAINT FK_StudentId FOREIGN KEY (StudentId) REFERENCES Person(PersonId) 
) 

CREATE TABLE IF NOT EXISTS Parents(PersonID INT NOT NULL , 
    PRIMARY KEY (PersonID) , 
    CONSTRAINT FK_PersonID FOREIGN KEY (PersonID) REFERENCES Person(PersonId) 
) 

Clave externa en subtipos personal, estudiantes, padres agrega dos condiciones:

  1. La fila de persona no se puede eliminar a menos que la correspondiente fila de subtipo no se elimine. Por ej. si hay una entrada de estudiante en los estudiantes tabla que hace referencia a la tabla Person, sin eliminar la entrada de estudiante la entrada de persona no se puede eliminar, lo cual es muy importante. Si se crea el objeto Student , entonces, sin eliminar el objeto Student no podemos borrar el objeto Person base.

  1. Todos los tipos de bases se han extranjera tecla "no nulo" para asegurarse de que cada base de tipo tendrá tipo de base existente siempre. Por ej. Si crea el objeto Student, primero debe crear el objeto Person.
Cuestiones relacionadas