схема и дизайн таблицы с полем auto_increment, которое не является ключевым - PullRequest
2 голосов
/ 27 сентября 2011

У меня есть номер счета, этот номер связан со специальным документом. Этот документ имеет идентификатор, который состоит из прогрессивного числа и текущего года, например:

222-2011
223-2011
224-2011
...

каждый год прогрессивный номер перезапускается с 1

1-2012
2-2012
3-2012

Во-первых, я подумал сделать таблицу с invoice_n, prog_n, year. prog_n - это AUTO_INCREMENT, и каждый год я сбрасываю его. Но вы не можете использовать поле AUTO_INCREMENT, которое не является ключевым. В любом случае, я собираюсь сбросить счетчик, и это не очень рекомендуется ...

Я не могу изменить формат идентификатора, я должен использовать это правило. Можно ли как-нибудь разработать эффективный дизайн?

среда классическая ЛАМПА

большое спасибо!

Ответы [ 2 ]

3 голосов
/ 27 сентября 2011

Расширяя ответ @Marius, я бы использовал триггер, чтобы MySQL автоматически устанавливал номер счета следующим образом:

DELIMITER $$

CREATE TRIGGER bi_invoices_each BEFORE INSERT ON invoices FOR EACH ROW
BEGIN
  DECLARE lastest_invoice_number VARCHAR(20);
  DECLARE numberpart INTEGER;

  -- find lastest invoicenumber in the current year.
  SELECT COALESCE(max(invoicenumber),0) INTO lastest_invoice_number 
  FROM invoice 
  WHERE invoice_date >= MAKEDATE(YEAR(NEW.invoice_date)  ,1) 
    AND invoice_date <  MAKEDATE(YEAR(NEW.invoice_date)+1,1);

  -- extract the part before the '-'
  SET numberpart = SUBSTRING_INDEX(lastest_invoice_number,'-',1)

  SET NEW.invoicenumber = CONCAT(numberpart+1,'-',YEAR(NEW.invoice_date));
END $$

DELIMITER ;

Обратите внимание, что вы не можете получить доступ к автоматически увеличивающемуся идентификатору в before триггере;
Только в триггере after вы можете сделать это, но там вы не можете изменить никакие значения, поэтому требуется небольшая хитрость.
Было использовано больше хитрости, чтобы убедиться, что мы используем invoice_date как есть в запросе выбора, чтобы можно было использовать индекс для этого поля.

См:
http://dev.mysql.com/doc/refman/5.0/en/string-functions.html#function_substring-index
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html#function_makedate

3 голосов
/ 27 сентября 2011

Вы можете иметь отдельный столбец id с auto_increment в таблице счетов и триггер, который заполняет prog_n по следующей формуле:

prog_n = id - select max(id) from invoices where year = current_year - 1

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...