2010-09-20 2 views
0

Моя объектная модель приведена ниже и хотела бы, чтобы ваши входы на число индексов создавали для более быстрого ответа на запросы (по h2, mysql). Допущения и вопросы приводятся ниже следующей модели.Сколько индексов должно быть создано для более быстрых запросов.

@Entity 
@Table(name = "user") 
public class User { 

    @Id 
    @GeneratedValue(strategy = IDENTITY) 
    @Column(name = "id", unique = true, nullable = false, insertable = false, updatable = false) 
    private Integer id; 

    @ManyToOne(fetch = FetchType.LAZY) 
    @ForeignKey(name = "fk_user_org_id") 
    @Index(name = "idx_user_org_id") 
    @JoinColumn(name = "org_id", nullable = false, referencedColumnName = "id") 
    @NotNull 
    private Organization organization; 

    @ManyToOne(fetch = FetchType.LAZY) 
    @ForeignKey(name = "fk_user_year_id") 
    @Index(name = "idx_user_year_id") 
    @JoinColumn(name = "year", nullable = false, referencedColumnName = "id") 
    @NotNull 
    private Year year; 

    @ManyToOne(fetch = FetchType.LAZY) 
    @ForeignKey(name = "fk_user_created_by") 
    @Index(name = "idx_user_created_by") 
    @JoinColumn(name = "created_by", nullable = false, referencedColumnName = "id") 
    @NotNull 
    private User createdBy; 

    @Column(name = "name", nullable = false) 
    private String name; 

    @Column(name = "desc") 
    private String desc; 

    @Column(name = "is_system", length = LEN_1) 
    @Type(type = "org.hibernate.type.YesNoType") 
    private boolean isSystem = false; 

    @Column(name = "user_type", nullable = false) 
    private UserType userType; 

    @Column(name = "status", nullable = false) 
    @NotNull 
    private Status status; 

} 

Наш план состоит в использовании нескольких индексов столбцов вместо индекса одного столбца (т.е. создать индекс user_idx на основе (организация, год, IsSystem, статус, UserType, CreatedBy)). Предполагая, что у меня есть этот индекс, я получу оптимизированные ответы для моих запросов, перечисленных ниже.

  1. выбрать * от пользователя где организация = 1 и год = 2010;
  2. выберите * от пользователя где организация = 1 и год = 2010 и isSytem = true или false; (т.е. пользователи системы или пользователи, определенные приложением)
  3. выберите * от пользователя где организация = 1 и год = 2010 и isSytem = false и userType = Manager (т.е. все менеджеры)
  4. выбрать * от пользователя где организация = 1 и год = 2010 и isSytem = ложь и UserType = Сотрудник (т.е. все сотрудники)
  5. выберите * от пользователя, где организация = 1 и год = 2010 и isSytem = ложные и UserType = Менеджер и статус = ACTIVE (т.е. активные пользователи)
  6. выберите * от пользователя где организация = 1 и год = 2010 и createdBy = 'Sam' или 'Joe' Требуется ли [6] другой индекс нескольких столбцов, состоящий из трех столбцов?

  7. Поскольку мы создаем индекс нескольких столбцов в соответствии с моим первоначальным допущением, могу ли я безопасно удалить отдельные индексы (idx_user_org_id, idx_user_year_id, idx_user_created_by), которые в настоящее время определены в модели?

+1

EXPLAIN - ваш лучший друг здесь – Mchl

ответ

2

Вы должны изменить порядок столбцов в индексе:

(organization, year, isSystem, userType, status, createdBy) 

Это позволяет ему лучше обслуживать эти два запроса:

select * from user where organization=1 and year=2010 and isSystem=false and userType=Manager 
select * from user where organization=1 and year=2010 and isSystem=false and userType=Employee 

Does [6] необходимость другой индекс столбцов, состоящий из трех столбцов?

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

можно безопасно удалить отдельные индексы

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

+0

Хорошо, как [6], если я создаю индекс с несколькими столбцами, используя (организация, год, createdBy), это будет использоваться вместо предыдущего индекса. Я прав? – user339108

+0

@ user339108: Вероятно, он будет использовать этот индекс, да. Вы должны запустить 'EXPLAIN SELECT ...', чтобы узнать наверняка. –

+0

Я попытался добавить новый индекс нескольких столбцов для разрешения [6], и после этого все запросы, похоже, используют новый индекс нескольких столбцов для запросов, упомянутых в [1-5]. Это не кажется правильным? Дай мне знать, что мне здесь не хватает? – user339108

Смежные вопросы