I have a problem with designing database (SQL/MySQL). Let's assume we have a user, user can have many friends and many posts and filled some data about himself.
It's quite obvious that for friends
we need one pivot_table for n:n relation, for posts
we need to create one extra table with user_id (1:n) relation.
So we need users
, user_friends
and posts
tables. This is obvious. This is how relations should be handled.
But now let's assume we want for users to have the following data:
name - text
description - text
marital status - select only one from list
favourite colour - select only one from list
hobby - select up to 3 from list
For text fields (name, description) it's really obvious we simply create varchar/text columns in users
table and that's it.
The general question is: how the other fields (chosen from lists) should be handled? Should I create relations for them or maybe should I create standard data columns with them?
In my opinion there is no point to create relation tables for that because using lists (select) we only limit user when he can in fact paste into database. In theory we could allow user to manually input as favourite colour his colour (for example red
and if he types something wrong for example reds
we would compare it will list of allowed colours
). The same would be for gender - there is no point in my opinion to create extra table when we hold only woman and man and create relation for it.
First DB design:
I could for example create the following columns for properties:
marital_status - int
fav_colour - int
hobby_1 - int
hobby_2 - int
hobby_3 - int
And have one other table (or even plain array in PHP or other language) where I store that value 1 for fav_colour is for example red, value 2 for hobby is music and so on (it doesn't matter how I store those values here - I could also use enum
type for that) .
For me benefits for such attitude is not creating many relations that are in fact rather properties and not relations (as I mentioned above), so less work + easier getting information about user - you don't need to use any joins what would be important if you have for user for example 20 or 100 such properties and I can search in user table very easy. Disadvantages are also quite obvious - data is not normalized, for any multi selection (as for example hobby) I need to create 3 columns and if in future I decide that user can select not 1 colour but 2 or 3, I would need to add 2 extra columns.
Alternative DB design:
I create extra tables: colours
, hobbies
, marital_statuses
and I create 3 pivots tables: user_colours
, user_hobbies
, user_marital_statuses
. Disadvantages: many joins. Advantages - if I created 3 extra pivot tables I I could easily allow user to select up to 10 colours and I don't need redesign database at all. But disadvantages also occur - difficult searching, a lot of work, many joins.
Detailed question
So to sum up - what solution would be better assuming:
- I would probably not change the maximum count of one properties (if I decided I allow maximum 3 hobbies, this won't probably ever change)
- Lists of choices for many fields would be relative short (for most of them less than 10)
- I need to search a lot in such database. Someone for example wants to search user that have fav_colour set to red and have hobby music.
If there are any other solutions or advantages/disadvantages you see I appreciate to share with me.