I have a question about a database design in MySQL.
There are two groups of people i have a separate table for. Call them TABLE student and TABLE professor.
I can give each of them assignments from TABLE assignments.
Each person in each group can have multiple assignments, and each assignment can have multiple people. So to keep track of these, I have two mapping tables, call them TABLE student_assignment and TABLE professor_assignment.
My question comes here. I have a single table TABLE assignment_results that I want to store the results from all the assignments in. I would like for each line of each mapping table to have a single record...so it seems to make more sense to have a separate results table for each group of people??? TABLE prof_assign_results and TABLE stud_assign_results
Or would it make sense to combine the mapping tables and avoid splitting altogether? Is it possible to define a unique index containing three columns? Would the NULL values (in either the student or professor columns) interfere with that?
Related
I am currently working on a PHP/MySQL project for an assignment. In studying the efficient design of databases while working on the assignment I notice that in many cases it is good practice to create a third table when working with only two sets of data.
For example, if we have a table for "Students" and a table for "Addresses" it appears to be a good idea to create a third table i.e. "Student_Addresses" since a student can hypothetically have more than one address (separated parents etc.) and a single address can represent more than one student (siblings).
My question is: How do we go about populating that third table? Is there a way that it is done automatically using primary and/or foreign keys?
I've tried Google and my textbook to understand this but I've gotten nowhere. Links to tutorials or articles would be greatly appreciated.
Thanks for your help. I hope the question and example are clear.
n:m or 1:m normalization rule
Option 1:
user table
id
f_name
s_name
......
user address table
id
user_id // this should be index only as foreign keys will allow 1:1 only
address line 1
address line 2
address line 3
address_type (home, office ....)
Option 2:
user table
id
f_name
s_name
......
address table
id
address line 1
address line 2
address line 3
address_type (home, office ....)
user_address table
userId
addressId
according to your description option 2 would be the right solution. After adding the data to user table and address table then you need to add the data to user_address table manually. Some Object relational mapper (ORM) may do add the data to the third table automatically but you need to define the relations. check http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/reference/association-mapping.html.
http://docstore.mik.ua/orelly/linux/sql/ch02_02.htm
http://www.keithjbrown.co.uk/vworks/mysql/mysql_p7.php
You can save the data in the third table using triggers when the data is inserted/updated/deleted in your base tables. You can learn more about triggers at
mySQL Triggers
However in your case it would be better if you could write the logic at the application/code level to make an entry in the third table. You can set up foreign key relationships to this table from your base tables so that the data remains consistent.
There is no native method in MySQL to populate Student_Addresses in your situation - you have to take care of entering data (connections) by yourself, but you can use - for example - transactions - see answers in this topic: SQL Server: Is it possible to insert into two tables at the same time?
For taking care of connections consistency - in Student_Addresses make not-null fields for relations to ID from Student and ID from Address, make both of these field as unique key together and use ON UPDATE CASCADE and ON DELETE CASCADE. This will take care of removing records from junction table when removing records from any of two other tables and also won't allow you to add same address to the same student twice.
I don't think data will be populated automatically rather it's responsibility of user to insert data.
I am note sure about PHP but using Hibernate and Java this can be done seemlessly. Since data of Students and addresses could be coming through some web application Hibernate can map java objects to records in table and also populate relationship table.
I have to join multiple tables, some with one to many mappings, and convert every entry in the joined table to a single row entry in a csv file using PHP.
I know I am basically going from a 3D to 2D representation, but it is a formatting requirement for the csv file.
The MySQL structure consists of tables "questions", "people" and "trips". "people" table is linked to "questions" table by the id of "questions". Also in the same way "trips" is linked to "people" by the id of "people". There are one to many relationship between both "questions" to "people" and "people" to "trips"
The idea is to have a csv file with one "question" entry per row. This row entry will be the joined result of all 3 tables. The number of people and trips per questions entry is not consistent, therefore spaces are required if there are fewer people in some "questions" entries than other. The same with the trips.
What is the best way to get this done in PHP, except for brute force coding this with many queries, for loops etc. I am trying to get the MySQL query going, but cannot wrap my head around this problem.
I think you're looking for mysql GROUP_CONCAT function.
Select data with joins, group it by question_id and use group_concat on people and trips columns.
So I have 2 tables in my database, they are 'workouts' and 'exercises'. Workouts contains a row called exercises which is a comma-separated list of exercise IDs - from the 'exercises' table e.g. '1,2,3'.
My question is, can I write a single query to allow me to select a row from the workouts table, say one with an id of 1, and have MySQL fetch each of the exercises from the list in that row, returning them within the 'workout' row?
At the moment I'm using PHP to select the workout row, and then making individual requests for each of the exercises, resulting in serious inefficiency.
I took a look at Joining rows as array from another table for each row and also did some research into the group_concat() function, but I'm not sure that's what I'm after.
Update
Here are the 2 tables:
IMO, the best approach is to redesign your schema to have a cross-reference table called exercises_workouts (or something similar). Remove the CSV field.
Here's page that goes into more detail on implementing a many-to-many relationship:
http://www.tonymarston.net/php-mysql/many-to-many.html
Note: The linked page uses the mysql_* functions, but the general explanation of the approach stands. You'll want to look into PDO for database access.
I'm creating a game in actionscript that requires the use of an external database to store user details and scores.
This database will contain multiple tables, currently there are two.
My first table contains the headers - ID, email, username, password.
My second table contains the headers - ID, lvl1Score, lvl2Score, lvl3Score.
In my game, when a new user is created it creates an entry in the first table with the ID auto-incrementing.
My question is - Is there anyway to automatically create an entry in my second table with its default values and the same ID when I add to my first table?
I've read about joins, but everything i've read just talks about looking up data over multiple tables.
Also, is my table structure correct in the sence that the ID value can be used using the JOIN keywork to look up an entry from both tables.
I would suggest you to go for triggers.
create or replace trigger trigger_name after
insert on table1
for each row
begin
insert into table2 values(new.id,"value for lvl2score","value for lvl3score");
end
Something like this.
If the tables truly have a one-to-one relation, I would recommend that you simply make one table having all the fields.
Or did you mean this should store multiple scores for each individual user? In this case, you should not insert a default record for the user. Instead, the score.ID field should instead reference user.ID and allow duplicates.
I suggest you to use triggers and for more flexibility create a many-many relationship between "user" and "level", so you will end up with 3 tables:
user
level
user_level (this will contain the foreign keys: user_id, level_id)
I'm new to programming so forgive my simple questions.
Basically, I have two different tables containing data related to one another. I'd like to create a new column called "id" which will associate rows in both tables so that I can appropriately display the data.
When a user takes an action, a row is inserted into both tables.
What kind of properties should "id" have? Primary key, auto-increment on both tables or one table? How do I ensure that the same ID is inserted into both rows, do I insert into table1 first, then grab that ID and insert into table2?
Any help appreciated. Thanks
It's somewhat difficult to answer your question without knowing what the two tables contain, but I suggest you read about database normalization.
Regardless of how many tables you decide to have, each table should have an id column of some sort. Having a way to uniquely refer to a single row makes life a lot easier down the road when you need to make changes to the data. Auto-increment saves you from having to come up with your own unique primary key values.