I am creating a site where each registered user can store a list of contacts. It occurred to me that rather than storing the contacts in a table with user_id, contact_name, contact_email, it would be better to normalize it to prevent the same names/emails being stored multiple times. As a result, I now have 4 tables: users, names, emails and contacts where contacts contains user_id, name_id and email_id. Am I heading in the right direction, or am I complicating things needlessly?
Thanks for all the helpful responses to what I can see now is a pretty nebulous question. It may be a good idea to explain my reasoning.
In an example scenario, where there are 100 users, most of whom have joined though the recommendation of another user, there will be a large number of common email addresses shared by each users contact lists. However, johnsmith#email.com, may be known as John, J Smith, Johnny boy etc. by different users. If I understand the principles of normalization correctly (unlikely) the separation of user, contact name, and email address in to separate tables, should reduce duplicate entries significantly and make the database more efficient. In the example below, the Contacts table could contain the same email addresses multiple times.
So, to cut a long story short, is it better to have more entries than necessary in one table or several smaller tables without duplicate entries?
You're probably needlessly complicating things: I'd recommend one table for users, one for contacts and a join table to allow a many to many relationship between the two. If contacts are not shared between users it'd be acceptable to have the user id as a foreign key in the contacts table.
Hope this helps
You can do like this
1] User_info Table
User_Id | name
2] Contacts Table
Contact_Id | Contact_Name | Contact_Email
3] User_Contact Table
User_Id | Contact_Id
Can contacts have same email but distinct names, or vice-versa ? If not, i suggest two tables (users and contacts) linked by an associative table :
USERS
- userId
- userName
CONTACTS_USERS
- userId
- contactId
CONTACTS
- contactId
- contactName
- contactEmail
With foreign key constraints on userId and contactId you can achieve a robust linkage between the two tables, where each contact may be used by distinct users and where each user may have distinct contacts.
Related
If a user can have multiple addresses and phone numbers, is it possible to design the database in such a way that I can enforce integrity between data?
For example:
users(id,name)
addresses(id, description, user_id -FK to users)
phones(id, description, user_id -FK to users)
orders(id,address_id -FK addresses,phone_id - FK to phones)
How can I be sure that in the orders table I won't accidentally insert a record with user1 address and user2 phone number?
I'm sorry if this was asked before but I don't know how to search for this situation.
Where is the Orders table? It will have columns user_id, address_id, and phone_id.
For data entry, if a known user calls in an order, then the UI brings up the existing addresses and phones for that user. The order-taker can quickly click on them. Or the user can say to use a different address. Then the UI assists in adding a new address for that user.
Suppose there are three tables.
table 1
generic_ids
generic_id
table 2
companies
company_id
company_name
company_account_no
etc.
table 3
employees
employee_id
first_name
last_name
middle_name
position
etc.
An employee and a company have their own addresses (sometimes a number of addresses), so i put them into a separate table called addresses. To avoid having two tables, like company_addresses and employee_addresses, i thought my generic_ids table could generate ids for both companies table and employees table. Then i could join the companies table with the addresses table or employees table with addresses table and always differentiate between joining companies with addresses and employees with addresses.
There are a number of other attributes, like address.
Is it a bad idea to do it like this? Some suggestions, improvements, better ways?
Two ways to do what you want that is probably easier/more efficient.
1) Make the id's in both tables auto increment, but with the increment in one of the tables starting so high, the first table will never reach it.
2) You can also differentiate with them having them same ID when you join the tables, by doing something like:
select concat("c",company_id) from companies
select concat("e",company_id) from employees
Then there's no conflict. In my opinion adding foreign keys just for categorization is a bad idea.
I have a pretty typical user table setup for my web application:
user_id | username
--------------------
0 greg
1 john
... ...
Both fields are indexed and unique, so I can look up a user by id or username quickly.
I want to keep a friends table, and am not sure whether to store the user_id values or usernames in that table:
user_id_1 | user_id_2
--------------------------
or
username_1 | username_2
--------------------------
I am going to want to get a list of friends for a user, so it would be convenient to immediately have the usernames in the friends table instead of doing a join on the users table:
select * from friends where username_1 = 'greg';
If I'm storing user ids, I need to do a join then to get the usernames - will that be costly?:
select * from friends
where user_id_1 = x
join users where user_id = { all those results }
Using user ids allows me to let users change usernames flexibly, but I'm not letting them do that anyway. Any advice would be great.
Thanks
A join on the IDs won't be too bad. The ID may be smaller to store on disk. Also, I would imagine a list of friends would have something other than just user names, in which case, you have to join no matter what.
Well, as you said, using id semantics means you can change the username without having to deal with cascading effects. For most cases PK / UNQ + FK indexes will make joins thundering fast, but you may have a point for huge tables (for which you will eventually need some kind of external index, or other tool anyway).
The ID will be smaller if you use numeric values. Also the index search will be faster. Here you'll find the data types for MySQL 5.0.
Also I don't know how are you using index, but I'd recommend to add and auto-increment field. You can do that to a table, for an integer index like this:
ALTER TABLE `Database`.`tableName` ADD COLUMN `indexName` INTEGER NOT NULL AUTO_INCREMENT
I am building a database for a web application that includes users following each other. What would be a good design? I was thinking this:
TABLE: users ROWS: user_id, name, pass, email, activated, user_level, registration_date
TABLE: relationships ROWS: relation_id, user_id, followed_id
What do you think of that?
For the user table, I guess what you have is correct. If you need to add more columns, you could simply alter that table, or add an additional table with a one to one relationship.
As for the relationships table, I think that is correct. Although i wouldn't call it followed_id. I would suggest that you could use that table for many different types of interactions, so I would call it user_id and interacter_id and the relationship_id would be a number of different types of interactions (follow, poke, etc).
I'm new to database design,
please give me advice about this.
1 When should I use a composite index?
im not sure what does index does, but
i do know we should put it when it
will be heavly loaded like for WHERE
verified = 1 and in search like
company.name = something. am i right ?
2 MySQL indexes - how many are enough?
is it just enough ?
3 Database Normalization
is it just right?
Thanks.
edit*
rules.
each users( company member or owners ) could be a member of a
company
each company have some member of users.
there are company admins ( ceo, admins) and there are company members
( inserts the products )
each company can have products.
for the number 3 i will add a bit at users_company
- 1 is for admin
- 0 is for members
Looks good, well normalised, to me at least.
I notice that each product can only belong to one company. If that's what you intended that's fine, otherwise you could have product have its own PID and have a product_company relation table, which would let more than one company sell a particular product. Depends who administers the products I guess.
I did notice that the user table is called 'users' (plural) and the others are singular ('company', 'product'). That's only a minor thing though.
The only comment I have is that you may want to consider just adding a mapping_id column to your users_company table and making CID and UID foreign keys, and add a UNIQUE constraint.
This way you can have a distinct Primary Key for records in that table which isn't dependent on the structure of your other tables or any of your business logic.