Разбиение в SQL Server 2005 - PullRequest
       14

Разбиение в SQL Server 2005

0 голосов
/ 20 января 2009

У меня есть несколько вопросов о разделении и стратегии, как и когда его использовать. Как я понял из Секционированных таблиц и индексов в SQL Server 2005 , секционирование используется не только для управляемости, но и для повышения производительности очень больших таблиц базы данных (VLDB). У нас есть таблица с миллионами записей. В этой таблице хранятся данные о производительности, например, сколько раз был указан элемент при нажатии и т. Д. Нам нужно ежедневно оценивать эти данные за текущий месяц в реальном приложении. Я хочу предотвратить перемещение данных из одной таблицы в другую только из-за производительности. Моя идея была: я создаю раздел на этом VLDB по месяцам за текущий год. Затем я бы создал кластерный индекс по полю даты таблицы и схеме разбиения. Я не знаю, правильно ли я понимаю, но я исключаю, что этот индекс будет создаваться отдельно для каждого раздела.

Как выглядит мой код на этапе разработки.

/*
Maybe it looks like complicated, but instead of static upper bound, 
I use function to determine end of the month for the current year.

So for example (executed in year 2009)
    SELECT DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1901)*12)+1-1,31-1)) 
returns 
    2008-01-30 23:59:59.997
*/
CREATE PARTITION FUNCTION PartitionMonthlyCurrentYear(DATETIME) AS
RANGE LEFT FOR VALUES
(
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1901)*12)+1-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+1-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+2-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+3-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+4-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+5-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+6-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+7-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+8-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+9-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+10-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+11-1,31-1)),
    DATEADD(ms, -2, DATEADD(month,((DATEPART(YEAR, GetDate())-1900)*12)+12-1,31-1))
);

/*
Create scheme on the primary file group. I'm aware about performance issues of this.
*/
CREATE PARTITION SCHEME SchemeMonthlyCurrentYear 
AS PARTITION PartitionMonthlyCurrentYear
ALL TO ([PRIMARY]);

/*
Create clustered index on table and scheme
*/
CREATE CLUSTERED INDEX [IX_Log_Seiten_archive_Datum] ON [dbo].[Log_Seiten_archiv] 
(
    [Datum] DESC
)ON SchemeMonthlyCurrentYear(Datum)
GO

Мои вопросы:

  1. Что вы думаете об этом подходе?
  2. Как удалить таблицу из указана схема разбиения? Если я удаляю индекс, я все равно не могу удалить схему и функцию, потому что все еще существует зависимость от таблицы Log_Seiten_archiv
  3. Как мне назначить таблицу для использования другой функции секционирования? Из-за разработки мне часто приходится менять способ определения функции разделов или создавать новую. Как я могу сделать это для существующей таблицы? Например, я хочу изменить год для функции, которую я показывал ранее.

С уважением Антон Калчик

Ответы [ 2 ]

2 голосов
/ 20 января 2009
  1. Вы не можете создавать функции секционирования SQL Server с недетерминированными функциями, такими как getdate (). Если вы заполнили базу данных данными за 10 лет, а затем просто остановились и наблюдали, как SQL Server работал в течение нескольких лет, вы увидите, что SQL Server перемещает эти данные из одного раздела в другой по мере изменения дат. Разделение SQL Server не работает таким образом. Когда вызывается функция раздела, данные помещаются в определенный раздел, и на этом все. Он не перемещается снова, если вы не хотите перемещать его вручную.

  2. Чтобы удалить разбиение таблицы, примените новый кластеризованный индекс, в котором не используется схема разбиения. Данные будут перемещены. (Имейте в виду, что это займет много времени в зависимости от размера ваших данных и скорости ваших дисков - для многотерабайтного хранилища данных мы, вероятно, будем говорить часами, если не днями.)

  3. Чтобы назначить другую функцию секционирования, вы применяете новый кластеризованный индекс, используя новую функцию секционирования. Опять же, тем не менее, если вы часто меняете функции секционирования, перестройка займет много времени, и секционирование, вероятно, не тот ответ, который вы ищете.

Секционирование - это отличное решение для> 100 миллионов баз данных строк с отдельными наборами дисковых массивов, но, похоже, вы просто размещаете все на одном наборе дисков, в одной файловой группе. Вы не увидите там большого увеличения производительности.

Также следует помнить, что разбиение на разделы доступно только в SQL Server Enterprise Edition, а не в Standard. Он доступен в Dev, но вы не можете использовать его в производстве из-за лицензионных ограничений.

0 голосов
/ 22 января 2009

спасибо за быстрый ответ.

  1. Вы правы, что разработчик несет ответственность за то, как данные будут переноситься в многораздельную таблицу. Существует множество подходов к этому, и каждый из них имеет свои преимущества и недостатки. Я нашел отличную статью об этом на Technet .

Теперь я понял, как я могу удалить или переназначить функцию раздела.

Вот пример:

Создать раздел на существующей таблице:

CREATE CLUSTERED INDEX [IX_Log_Seiten_archive_Datum_Kanzleinr] ON [dbo].[Log_Seiten_archiv_Daily] 
(
    [Datum] DESC,
    [kanzleinr] ASC
)ON SchemeDailyCurrentYear(Datum) 
GO

Удалить раздел на существующей таблице:

DROP INDEX [IX_Log_Seiten_archive_Datum_Kanzleinr] ON [dbo].[Log_Seiten_archiv_Daily];

CREATE CLUSTERED INDEX [IX_Log_Seiten_archive_Datum_Kanzleinr] ON [dbo].[Log_Seiten_archiv_Daily] 
(
    [Datum] DESC,
    [kanzleinr] ASC
)ON [PRIMARY]
GO

Спасибо за помощь AKA

...