Take the 2-minute tour ×

could someone give me an idea how to create this database structure. Here is an example:

Table "countries":
id, countryname
1, "US"
2, "DE"
3, "FR"
4, "IT"

Now I have another table "products" and in there I would like to store all countries where this product is available:

Table "products":
1,"product1",(1,2,4) // available in countries US, DE, IT.
2,"product2",(2,3,4) // available in countries DE, FR, IT.

My question: How do I design the table structure in "products" to be able to store multiple countries?

My best idea is to put a comma-separated string in there (i.e. "1,2,4"), then split that string to look up each entry. But I doubt that this the best way to do this?

EDIT: Thank you all for your help, amazing! It was difficult to choose the right answer, I finally chose Gregs because he pointed me to a JOIN explanation and gave an example how to use it.

share|improve this question
add comment

5 Answers

up vote 6 down vote accepted

You need an intersection table for that many-to-many relationship.

Table Country
CountryID, CountryName

Table CountryProduct
CountryID, ProductID

Table Product
ProductID, ProductName

You then Inner Join all 3 tables to get your list of Countries & Products.

Select * From Country 
Inner Join CountryProduct On Country.CountryID = CountryProduct.CountryID 
Inner Join Product On CountryProduct.ProductID = Product.ProductID
share|improve this answer
add comment

Without denormalizing, you'll need to add an extra table

Table Product countries
ProductID CountryID
1         1
1         2
1         4...
share|improve this answer
add comment

What you're talking about is normalisation. You have a many-to-many structure, so you should create another table to link the two. You should never (ok, pretty much never) use delimited strings to store a list of values in a relational database.

Here's an example of the setup:

product_countries table

productid | countryid
1         | 1
1         | 2
1         | 4
2         | 2
2         | 3
2         | 4

You can use a foreign key to each other table, then make them both into a composite primary key.

You can then get a list of supported products for a country ID like this:

SELECT * FROM products, product_countries
WHERE products.id = product_countries.productid
AND product_countries.countryid = $cid
share|improve this answer
why not using a join? this always looks a bit odd to me –  Flo Nov 9 '11 at 9:09
The logic when using a JOIN would be more confusing to an SQL newbie, which the OP clearly is. Sure, a JOIN would work too, but without it the logic is clearer and easier to understand. –  Polynomial Nov 9 '11 at 9:11
Thank you and all others for helping!! Yes, SQL-newbie here. One subquestion: That SQL-statement seems slow to me - suppose I have 100000+ products, wouldn't that take a long time to iterate through product_countries? –  marimba Nov 9 '11 at 9:21
Shouldn't do. Since both columns are both primary and foreign keys, they'll be indexed. –  Polynomial Nov 9 '11 at 9:25
add comment

You could also make a third table countries_products with fields country_id and product_id.

share|improve this answer
add comment

the best approach for relational databases is the following :

One table for coutries, let's say country_id, country_desc (country_id is primary)

one table for products, let's say product_id, product_desc and as many columns as you want (product_id is primary)

if you had only one country for sure, it'd be enough to have a foreign key pointing to country_id in each product row. Having a foreign key asserts that there is an actual country behing a country_id referring to country table.

In your case you have several countries for a product, so add a separate association table product_id, country_id

both keys primary and both foreign as well.

share|improve this answer
add comment

Your Answer


