Как организовать структуру базы

dmonco
Дата: 22.01.2013 05:02:19
Помогите исправить ошибки и правильно организовать небольшую базу, чтобы понять логику процесса.

Исходные данные:
название лотереи (например, лото Мега-Сена)
континент (например, Северная Америка)
страна (например, США)
название валюты (например, доллар)
символ валюты (например, $ или USD)
минимальный джекпот (например, 10000000 - десять миллионов)
рекордный джекпот (например, 100000000 - сто миллионов - данных может не быть, поле останется пустым)
потенциальный джекпот (например, 10000000 - десять миллионов - данных может не быть, поле останется пустым)
следующий джекпот (например, 100000000 - сто миллионов)
дни проведения (понедельник, вт, ср, чт, пт, сб или воскресенье)
время проведения (наример, в 14:00)
дата проведения (10 августа 2012)
результат розыгрыша (например, 5,6,4,2,4,5 и бонусные номера 10 и 12 или 5,6,4,2,4 и только один бонусный номер 10, везде формат лотерей разный)


Логика у меня была такой:
1. Создаем для континентов таблицу. Континенты внесу сразу в базу, редактироваться они не будут.

2. Страны - то же самое, создаем отдельно таблицу, данные внесу сразу, редактироваться не будут.
В этой таблице делаю привязку к континенту по id.

3. Для валюты - отдельно таблицу:
- название валюты
- символ валюты
Так как планирую с админки добавлять, убирать валюту или опубликовывать, также добавил поля:
- published
- дату создания валюты
- кем создана (ну, админ или другой юзверь)
- дата изменений (пишу для Joomla, там есть такой функционал)
- кем внесены изменения

4. Следующая таблица - дни недели.
- ид дня
- название (понедельник, вторник и т.д.)

5. Таблица по лотереям (лотереи будут добавляться или убираться с админки)
- ид лотереи
- название
- ид континента
- ид страны
- ид валюты
- минимальный джекпот (если есть данные)
- рекордный джекпот джекпот (если есть данные)
- потенциальный или другой джекпот джекпот (если есть данные)
- следующий джекпот (если есть данные)
- опубликована или не опубликована (1 или 0)
и стандарт когда создана, кем создана, когда внесены изменения и кем внесены изменения

6. Шестая таблица - дни розыгрыша. У некоторых три розыгрыша в неделю, у некоторых один раз в неделю.
- ид розыгрыша
- ид лотереи
- ид дня
- время проведения в этот день

7. И последняя таблица - результаты проведенных лотерей
- ид результата
- ид лотереи
- дата розыгрыша
- результат розыгрыша (здесь может быть что угодно, я в том плане, у некоторых 6 номеро, у некоторых лотерей 6 основных и два дополнительных шара, но не более 8 всего)

Из всего написанного, вот что я накуралесил:

CREATE TABLE `#__continents` (
  `continent_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `continent_name` char(64),
  PRIMARY KEY(`continent_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store continents';

CREATE TABLE `#__countries` (
  `country_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `country_name` char(64),
  `id_continent` int(10),
  PRIMARY KEY(`country_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store countries';

CREATE TABLE `#__currencies` (
  `currency_id` smallint(1) UNSIGNED NOT NULL AUTO_INCREMENT,
  `currency_name` char(64),
  `currency_symbol` char(4),
  `published` tinyint(1) NOT NULL DEFAULT '1',
  `created_on` datetime NOT NULL default '0000-00-00 00:00:00',
  `created_by` int(11) NOT NULL DEFAULT '0',
  `modified_on` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
  `modified_by` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`currency_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store currencies';

CREATE TABLE `#__days` (
`day_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`title` varchar(255) NOT NULL DEFAULT '',
  PRIMARY KEY (`day_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store days';

CREATE TABLE `#__lotteries` (
  `lottery_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `title` varchar(255) NOT NULL DEFAULT '',
  `continent_id` int(10),
  `country_id` int(10),
  `currency_id` int(11),
  `min_jackpot` int(12),
  `max_jackpot` int(12),
  `other_jackpot` int(12),
  `next_jackpot` int(12),
  `published` tinyint(1) NOT NULL DEFAULT '1',
  `created_on` datetime NOT NULL default '0000-00-00 00:00:00',
  `created_by` int(11) NOT NULL DEFAULT '0',
  `modified_on` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
  `modified_by` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`lottery_id`),
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store lotteirs';

CREATE TABLE `#__drawday` (
  `drawday_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `lottery_id` int(10),
  `day_id` int(10),
  `drawtime` datetime NOT NULL DEFAULT '0000-00-00 00:00:00'
  PRIMARY KEY (`drawday_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store days of draws';

CREATE TABLE `#__results` (
  `result_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `lottery_id` int(10),
  `drawdate` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
  `drawresult` varchar(255) NOT NULL,
  PRIMARY KEY (`result_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store results of draws';


Подскажите, правильно ли организовал структуру или есть ошибки?
И по полям правильно ли всё определил для создания таблиц?
javajdbc
Дата: 22.01.2013 07:40:30
вообше неплохо, для первой в жизни базы я бы сказал очень неплохо.

Далее, по мелочам:

-- почитайте про нормализацию, парочку разных учебников с примерами.
Ваша задача -- сначала сделать чтоб преподаватель поставил пятерку.

-- ставьте одинаковый ТИП примари кей и форенг ключей.
например ИНТ(11). Иначе потратите полдня на ошибку (кажется) номер 150.

-- ИнноДБ вроде как кузявее использовать

-- в лоторее связка на страну дотаточна, континент уже не надо туда.

-- если чиста по чесноку, то розыгрыш вообшето сыночек дро-дейт,
прада надо иметь тогда актив-нот-актив индикатор на дро-дейт таблице.
С другой стороны, если сделать как вы сделали, то результаты не
подвязаны к дро-дайт -- и последние могут менятся -- т.е. они
отражают конкретно текушее расписание.

Что верно а что не верно --- ыв поймете сами когда начнете пользоватся
таблицами на практике. Например хотите ли вы создавать новую (запись)
лоторею если изменилось расписание, или нет?

-- чар? наверно варчар кузявее.

-- если хотите специализироватся в разработке баз данных, то
учитесь сразу делать форенг-кейз, если вы просто веб програмист, то
не делайте форенг-ключей толькок мешать будут.
(правда ваш ДБА их все равно будет делать и ругать девелоперов матом,
я с ним соглашусь)
dmonco
Дата: 23.01.2013 08:54:36
Спасибо. Поисправлял некоторые ошибки.
Все идишнки с формата что-то_id в начале каждой таблицы перевел просто в id, соответсвенное primary key тоже id.
Просто при создании таблиц почему-то ругалось. Но не в этом вопрос.
1. Континенты мне нужны. В фронте планирую делать вывод лотерей по континентам.
2. Что такое нормализация? Может ссылочку скините, чё читать-то лил хотя бы что искать.
3. Не понял это - ставьте одинаковый ТИП примари кей и форенг ключей.
И что такое форенг ключи. Как на англияком правильно чтоб я погуглил?
4. Не понял про индикатор - актив-нот-актив
Мне как раз прошедшие розыгрыши нужно чтобы были подвязаны к дате.
К примеру, выбрал дату, выбрал лотерею, посмотрел - какие там были номера.
Мне для этого ещё в таблицу нужно поле какое-то добавить?
5. Да, конечно, планирую в админке в редактировании лотереи иметь возможность отметить дни в которые проводится и указать время для каждого дня. Если расписание поменялось, захожу в редактировать и буду менять.
dmonco
Дата: 23.01.2013 08:56:06
Уже нашел про FOREIGN KEYs
Читаю [url=]http://dev.mysql.com/doc/refman/5.5/en/innodb-foreign-key-constraints.html[/url]
tanglir
Дата: 23.01.2013 10:18:39
>Если расписание поменялось, захожу в редактировать и буду менять.
Тогда сразу продумывайте, как будете хранить историю уже прошедших лотерей (в структуру не вчитывался, так что, м.б., это там уже заложено, но сомневаюсь).

>Континенты мне нужны. В фронте планирую делать вывод лотерей по континентам.
Джойн на таблицу континентов, и всё.
>Что такое нормализация? Может ссылочку скините, чё читать-то лил хотя бы что искать.
Википедия "нормальная форма" и дальше по ссылкам.
>Не понял это - ставьте одинаковый ТИП примари кей и форенг ключей.
Если вы попытаетесь сделать в родительской таблице ид, к примеру, SMALLINT, а в дочерней ссылающееся поле сделаете просто INT, то мускль не сможет создать внешний ключ. Потому что он умеет делать внешние ключи только по полям одинакового типа.
dmonco
Дата: 23.01.2013 18:16:46
По истории вот таблица:
CREATE TABLE `#__results` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `lottery_id` int(11),
  `drawdate` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
  `drawresult` varchar(255) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 COMMENT='Used to store results of draws';

где lottery_id - ид лотереи
drawdate - дата и время проведения лотереи
По этому полю у меня вопрос. Этого достаточно или нужно разделить: одно поле для даты и одно поле для времени?
drawresult - результат в числах
Кроме PRIMARY KEY (`id`) мне понадобится здесь ещё какой-нибудь key?
javajdbc
Дата: 23.01.2013 18:52:50
dmonco,

1. у вас вполне приличная начальная база.
Приложите еше немного сил на нее и сразу начинайте
делать бизнес логику и юзер интерфейсы.

2. Никто никогда не делал базу данных "сразу правильную".
Она 100 раз поменяется.

3. про индексы -- все примари-кей автоматом индексятся
и сделайте индексы на ВСЕ форенг-ки (внешние ключи).
например в таблице результат надо индекс на лотори_ид.

4. Изначально всегда храните даты в одной ДАТЕТИМЕ колонке.
Может когда нибудь понадобится дополнительные
(избыточные) колонки года или месяца, но это потом-потом...

5. Если в таблице лоторея есть старна, то страна уже знает свой континент.
Это как раз тема "нормализация". Иногда эти правила
специально нарушают для удобства и оставляют обе связки:
на страну И на континент. Вообшето континент надо убрать
из лотореи.
Akina
Дата: 23.01.2013 19:05:49
javajdbc
страна уже знает свой континент

Россия
Казахстан
Азербайджан
Грузия
Турция
Египет
Панама
Индонезия
javajdbc
Дата: 23.01.2013 19:18:53
Akina
javajdbc
страна уже знает свой континент

Россия
Казахстан
Азербайджан
Грузия
Турция
Египет
Панама
Индонезия


Говорят есть дом где-то в центре Европы (Австрия?)
где межгосударственая граница проходит по кухне.
Прикинь, каково обитателям этого дома?
tanglir
Дата: 23.01.2013 20:07:04
javajdbc
Akina
пропущено...

Россия
Казахстан
Азербайджан
Грузия
Турция
Египет
Панама
Индонезия


Говорят есть дом где-то в центре Европы (Австрия?)
где межгосударственая граница проходит по кухне.
Прикинь, каково обитателям этого дома?
В Корееях такое здание есть для переговоров, недавно читал. Половина здания на Севере, половина на Юге. Гос. граница делит стол переговоров ровно пополам :)